Category Archives: iOS Development

How to use a specific voice for text-to-speech in iOS

There are two ways of creating voices with which we can make iOS talk: creating a voice using a locale (classic), or creating a voice using a specific voice identifier (futuristic).

Let me show you both options here.

Classic and Easy

In this snipped we’re creating a voice with a certain dialect, British English in this case:

NSString *phrase = @"I'm listening.";

AVSpeechSynthesizer *synthesizer = [[AVSpeechSynthesizer alloc]init];

AVSpeechUtterance *utterance = [[AVSpeechUtterance alloc]initWithString:phrase];

AVSpeechSynthesisVoice *voice = [AVSpeechSynthesisVoice voiceWithLanguage:@"en-GB"];

utterance.voice = voice;

[synthesizer speakUtterance:utterance];

While very straightforward, we don’t know if the voice is going to be male or female. All we can specify is the language and dialect.

Futuristic and Specific

The above works fine and probably was enough when the speech synthesiser framework was introduced in iOS 7, but since then there are a myriad of other voices we can use in our applications. To specify one of them, we need a voice identifier.

Here’s how to do it:

NSString *phrase = @"I'm listening.";

AVSpeechSynthesizer *synthesizer = [[AVSpeechSynthesizer alloc]init];

AVSpeechUtterance *utterance = [[AVSpeechUtterance alloc]initWithString:phrase];

AVSpeechSynthesisVoice *voice = [AVSpeechSynthesisVoice voiceWithIdentifier:@""];

utterance.voice = voice;

[synthesizer speakUtterance:utterance];

The setup is almost the same, but instead of the voiceWithLanguage method, we’re using the voiceWithIdentifier method here.

Finding Voices

To see a list of all available voices on the device, we can access the speechVoices method of the AVSpeechVoices class. This will return an array of AVSpeechVoices, all of which have a name, quality and identifier property. The latter is what we’re looking for so we can create a specific voice.

Here’s a method lists all available voices on the current device:

- (void)listVoices {

    NSArray *allVoices = [AVSpeechSynthesisVoice speechVoices];

    for (AVSpeechSynthesisVoice *voice in allVoices) {
        NSLog(@"Voice Name: %@, Identifier: %@, Quality: %ld",, voice.identifier, (long)voice.quality);


Not all voices may be installed on all devices. For example, Alex is an optional high quality voice that the user needs to download first before he will show up in this array.

The quality parameter either returns 1 for standard/low-res, or 2 for enhanced/hi-res voices. Again it is up to the user to enable the hi-res quality of a voice under Settings.

How to test if an NSArray or NSSet contains an object

There’s a handy method in the NSArray class that lets us check if an array contains a particular object or not. The containsObject method returns a BOOL for us to evaluate.

Consider this:

// create an array
NSArray *array = @[@"Apples", @"Pears" , @"Bananas"];

// check if Pears are in the array
if ([array containsObject:@"Pears"]) {
    NSLog(@"We have Pears.");

Likewise, we can check if our array does not contain a particular object by testing the opposite:

// check if Grapes are not in the array
if (![array containsObject:@"Grapes"]) {
    NSLog(@"But we don't have Grapes.");

Both the NSMutableArray and NSSet classes has the same method, so we can check for the (un-)presence of our objects in mutable arrays and sets the same way.

What’s new in iOS 10.2

iOS 10.2 introduces new features including the TV app (US Only), a new and unified experience for accessing your TV shows and movies across multiple video apps.

Emoji have been beautifully redesigned to reveal even more detail and over 100 new emoji have been added including new faces, food, animals, sports, and professions.

This update also includes stability improvements and bug fixes. Continue reading

How to turn an ISO language code into the language identifier

Oftentimes we deal with cryptic language abbreviations, such as en-GB or de-DE. While it’s more or less clear to us humans what this means, it would be nice to have a way to display something more readable to our users.

We can do this with a method from the NSLocale object. Consider this snippet:

NSString *code = @"en-GB";
NSLocale *locale = [NSLocale currentLocale];
NSString *translation = [locale displayNameForKey:NSLocaleIdentifier value:code];

NSLog(@"%@ is %@", code, translation);

// output:
en-GB is English (United Kingdom)

Here we translate en-GB into “English (United Kingdom)”. First we take the current device’s locale, then we use the displayNameForKey method to turn the ISO language code into a human readable description.

The beauty is that no matter what language the device is set to, iOS will display the translation in the matching locale. For example, on a German device, en-GB would be translated into “English (Vereinigtes Königreich)”. Even though Germans would probably never refer to the UK as that. But I digress.

This also works with abbreviated language codes, such as “en” (instead of en-GB). In that case, the output is simply “English” without the country identifier.

We can also force iOS to display the translation in a locale of our choice. Rather than using the currently selected locale on the device, we can pick one and display the output accordingly:

NSString *code = @"en-GB";
NSLocale *locale = [NSLocale localeWithLocaleIdentifier:@"fr-FR"];
NSString *translation = [locale displayNameForKey:NSLocaleIdentifier value:code];

NSLog(@"%@ is %@", code, translation);

// output:
en-GB is anglais (Royaume-Uni)

How to explode an NSString into single NSString characters

Say you had an NSString, and you’re interested in each single character. You’d think there’s a method for it, such as getCharactersInRange. Turns out that’s not really helpful, because it delivers unichar characters rather than NSStrings.

To extract single characters as NSStrings, we can use the substringWithRange method like so:

NSString *phrase = @"Complex stuff.";

// split NSString into its characters
for (int i=0; i<phrase.length; i++) {
    NSRange range = NSMakeRange(i, 1);
    NSString *character = [phrase substringWithRange:range];
    NSLog(@"Character is %@", character);


What’s New in iOS 10

iOS 10From the upgrade dialogue:

iOS 10 is the biggest release of iOS ever.

A massive update to Messages brings the power of the App Store to your conversations and makes messaging more personal than ever.

Find your route with beautifully redesigned Maps. Relive memories like never before in Photos. Use the power of Siri in more apps than ever. A new Home app to make controlling your home even easier. And all-new Music and News.iOS 10 introduces new features and improvements including:

Messages lets you express yourself in new ways and access your favorite apps right in your conversations

Siri now works with apps from the App Store to send messages, make phone calls, and more

Maps comes with an all new look and extensions to make reservations and book a ride

Photos is all-new with intelligent search making it easier to find people, places and more as well as new and beautiful ways to rediscover your memories

Home is a new app that lets you simply and securely manage your home automation products in one place

Apple Music has an all-new design, bringing greater clarity and simplicity to every aspect of the experience

Apple News has an all-new design adding bold typography, vibrant color, and distinct sections that make it easier to find stories on specific topics

Accessing the information you need is easier and quicker with a redesigned Lock Screen and deeper 3D Touch integration

QuickType keyboard adds new emoji, multi-lingual typing, and contextual predictions that leverage deep neural network technology

Suggested events and contact details are added to apps based on information found in Mail

Continue reading