Tutorial iOS – Criando um leitor de Textos

On 17 de setembro de 2014 by Conrado Carneiro

No tutorial de hoje iremos abordar como criar um aplicativo de leitura de textos automatizada.
De forma simples utilizando-se de funções implementadas no sistema é possível criar um aplicativo para realizar a leitura de textos, então mãos a obra!

Introduzido no iOS 7 a biblioteca AVSpeechSynthesizer produz uma voz sintetizada a partir de um determinado AVSpeechUtterance. Cada texto a ser lido pode ser ajustado a velocidade de leitura e o tempo de pausa entre as palavras lidas.
A primeira coisa que deve ser feita é importar a classe AVFoundation para isso basta acrescentar o código a seguir no cabeçalho da classe que irá ficar encarregada de fazer a leitura do Texto.

[sourcecode language=”objc” wraplines=”false” collapse=”false”]
@import AVFoundation;
[/sourcecode]

agora vamos adicionar a seguinte função ao código:

[sourcecode language=”objc” wraplines=”false” collapse=”false”]
– (void) playSintetizador {
NSString *texto = @"Ola Mundo!";
AVSpeechUtterance *utterance = [[AVSpeechUtterance alloc] initWithString:texto];
utterance.voice = [AVSpeechSynthesisVoice voiceWithLanguage:@"pt-BR"];

AVSpeechSynthesizer *speechSynthesizer = [[AVSpeechSynthesizer alloc] init];
[speechSynthesizer speakUtterance:utterance];
}
[/sourcecode]

O texto que será lido está armazenado na variável texto, do tipo NSString, para testar a função basta chama-la na função  viewDidLoad, conforme mostrado no código a seguir:

[sourcecode language=”objc” wraplines=”false” collapse=”false”]
– (void)viewDidLoad
{
[super viewDidLoad];
[self playSintetizador];
}
[/sourcecode]

Agora basta compilar o projeto e o texto Olá mundo será lido!

Porém vamos incrementar um pouco mais esse projeto e para isso vamos declarar o Delegate responsável em gerenciar o objeto AVSpeenchSynthesizer para isso vamos alterar algumas informações no arquivo .h e ele deverá conter as seguintes informaçoes:

[sourcecode language=”objc” wraplines=”false” collapse=”false”]
#import <UIKit/UIKit.h>
@import AVFoundation;

@interface ViewController : UIViewController <UITextViewDelegate, AVSpeechSynthesizerDelegate>
{
BOOL play;
}
@property (strong, nonatomic) IBOutlet UITextView *textView;
@property (strong, nonatomic) IBOutlet UIButton *lerButton;
@property (nonatomic, retain) AVSpeechSynthesizer *speechSynthesizer;
– (IBAction)cleanText:(id)sender;
[/sourcecode]

E deveremos também adicionar 3 elementos gráficos no projeto através do interface Builder, ficando da seguinte forma:

Captura de Tela 2014-09-17 às 16.30.06

O campo para digitar o texto é do tipo UITextView e a seguir foram declarados dois UIButton, porém o de Limpar Texto é do tipo IBAction e o de Ler é do tipo IBOutlet, a seguir iremos explicar o motivo da declaração ser diferente.

É fundamental linkar os objetos visuais ao código e já ensinamos anteriormente em nossos tutoriais.  No arquivo .M é que teremos as maiores alterações na função ViewDidLoad iremos alocar memória e iniciar objeto speechSynthesizer, em seguida chamaremos a função playSintetizador e por fim definir a função a ser chamada ao pressionar o botão Ler. Isso pode ser verificado no código a baixo:

[sourcecode language=”objc” wraplines=”false” collapse=”false”]
– (void)viewDidLoad {
[super viewDidLoad];
speechSynthesizer= [[AVSpeechSynthesizer alloc] init];
[self playSintetizador];
[lerButton addTarget:self action:@selector(playSintetizador) forControlEvents:UIControlEventTouchUpInside];
}
[/sourcecode]

Em seguida, temos as funções das ações dos botões:

[sourcecode language=”objc” wraplines=”false” collapse=”false”]
#pragma MARK – Buttons
– (IBAction)cleanText:(id)sender {
textView.text = @"";
}
– (void) playSintetizador {
if (!play) {
[lerButton setTitle:@"Pausar" forState:UIControlStateNormal];
play = YES;
NSString *string = textView.text;
if ([textView.text isEqualToString:@""]) {
string = @"Não há nada para ser lido!";
}
AVSpeechUtterance *utterance = [[AVSpeechUtterance alloc] initWithString:string];
utterance.voice = [AVSpeechSynthesisVoice voiceWithLanguage:@"pt-BR"];

speechSynthesizer.delegate = self;
[speechSynthesizer speakUtterance:utterance];
} else {
[lerButton setTitle:@"Play" forState:UIControlStateNormal];
play = NO;
[self.speechSynthesizer stopSpeakingAtBoundary:AVSpeechBoundaryImmediate];
}
}
[/sourcecode]

E por fim, as funções relacionadas ao Delegate

Função que chamada a cada leitura de palavra!

[sourcecode language=”objc” wraplines=”false” collapse=”false”]

– (void)speechSynthesizer:(AVSpeechSynthesizer *)synthesizer
willSpeakRangeOfSpeechString:(NSRange)characterRange
utterance:(AVSpeechUtterance *)utterance
{
NSMutableAttributedString *mutableAttributedString = [[NSMutableAttributedString alloc] initWithString:utterance.speechString];
[mutableAttributedString addAttribute:NSForegroundColorAttributeName
value:[UIColor colorWithRed:0.214 green:0.363 blue:1.000 alpha:1.000] range:characterRange];
textView.attributedText = mutableAttributedString;
}
[/sourcecode]

Função que é chamada quando a leitura começa!

[sourcecode language=”objc” wraplines=”false” collapse=”false”]
– (void)speechSynthesizer:(AVSpeechSynthesizer *)synthesizer
didStartSpeechUtterance:(AVSpeechUtterance *)utterance {
textView.attributedText = [[NSAttributedString alloc] initWithString:textView.text];
}
[/sourcecode]

Função chamada ao final da leitura

[sourcecode language=”objc” wraplines=”false” collapse=”false”]
– (void)speechSynthesizer:(AVSpeechSynthesizer *)synthesizer
didFinishSpeechUtterance:(AVSpeechUtterance *)utterance
{
self.textView.attributedText = [[NSAttributedString alloc] initWithString:self.textView.text];
[lerButton setTitle:@"Play" forState:UIControlStateNormal];
if ([textView.text isEqualToString:@"Não há nada para ser lido!"]) {
textView.text = @"";
}
play = NO;
}
[/sourcecode]

O resultado, visual pode ser visto no Gif a seguir:

test
Caso tenha interesse, o projeto completo está disponível no link. Qualquer dúvida é só postar nos comentários.

Deixe um comentário

O seu endereço de e-mail não será publicado. Campos obrigatórios são marcados com *