Utilizar uma extensão do Google Chrome é uma forma muito boa de criar um sistema com reconhecimento de voz. Isso porque não há nenhum custo envolvido e o resultado final é bem interessante.

Caso você não tenha lido o post sobre as diferentes formas de fazer reconhecimento de voz, passe lá para entender tudo que vou falar.


Características

Essa solução se trata de criar uma extensão no Google Chorme que será o cérebro do sistema. É por meio dessa extensão que o reconhecimento de voz será feito com a utilização da API da Google. A partir do resultado reconhecido, os comandos são enviados ao Arduino. E a ideia é conectar o Arduino no USB do computador e, comunicar com ele pelo serial.

Mas por que não criar apenas um arquivo HTML ao invés de uma extensão? Pois, é necessário utilizar a comunicação serial e, sem a extensão, não é possível.

Como foi dito no outro post, essa é uma solução computadorizada. Portanto, as desvantagens incluem os gastos de energia e a falta de praticidade em se usar o sistema. E, a vantagem está no fato de que é uma solução relativamente simples e sem custo.

Em relação as particularidades dessa solução, temos que: não é necessário instalar nenhum programa (se você já possui o Google Chrome); por ser uma extensão de navegador, o acesso à ela é indireto e mais demorado que o acesso ao sistema de outras soluções; é necessário saber um pouco de HTML e javascript para poder entender e alterar os códigos, e isso não é todo mundo que entende.

Além disso, o resultado final é bem melhor do que o Processing. Pois não é necessário ficar rodando nenhuma página de fundo para o programa funcionar, apenas a própria extensão. Ou seja, é uma solução mais “limpa”.


Como fazer

Antes, gostaria de deixar meu agradecimento ao blog do Fabio Biondi (o link saiu do ar, mas vou manter ele aqui por conta dos créditos ao autor), que foi de onde eu tirei quase toda a base para conseguir fazer essa solução.

Configurações e downloads EXTENSÃO

Estaremos lidando com códigos em HTML e javascript. E, apesar de ter dito que não é necessário instalar nenhum programa, é recomendável baixar um adequado para mexer com esses tipos de arquivos. Pois, o bloco de notas não apresenta uma formatação adequada e isso dificulta o entendimento do código. Recomendo o Notepad++ (bem leve e rápido).

Para ver a solução funcionando acompanhe as instruções abaixo e no final explico como modificar a extensão.

Clique aqui para baixar a extensão que desenvolvi. Com isso, é preciso adicionar a extensão ao navegador. Primeiro, clique no ícone de opções do Google Chrome e vá em Mais ferramentas -> Extensões.

como acessar as extensões

Feito isso, marque a caixa “Modo do desenvolvedor” e clique em “Carregar sem compactação”.

como adicionar extensões

Agora, extraia o arquivo baixado e escolha a pasta da extensão (que é a pasta extraída). E você deverá ver o seguinte:

extensão adicionada

Configurações e downloads ARDUINO

Para fazer o Arduino reconhecer os comandos é necessário fazer upload do código abaixo nele. Para entender o código, recomendo que leia o post sobre comunicação serial, além de ler os comentários. Código adaptado do blog do Fabio Biondi:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
/*
 * Codigo que liga e desliga um LED
 * a partir de comandos enviados pela extensão
 */


#define LED 13 // Pino do LED

void setup() {
  Serial.begin(9600); // Inicializa a comunicação serial
 
  // Define o LED como saida e deixa ele desligado
  pinMode(LED, OUTPUT);
  digitalWrite(LED, LOW);

  printLEDStatus(); // Executa a funçao que informa o estado do LED via serial em formato JSON (para a estensão fazer a leitura)
}

void loop() {
  if (Serial.available() > 0) { // Se tem alguma mensagem para ler

    char incomingByte = Serial.read(); // Grava a leitura na variavel incomingByte
   
    if (incomingByte == 'y') { // Se o resultado lido foi 'y'
      digitalWrite(LED, HIGH); // Então, acende o LED
    } else if (incomingByte == 'n') { //Se foi 'n', apaga o LED
      digitalWrite(LED, LOW);
    }
    printLEDStatus(); // Executa a funçao que informa o estado do LED via serial em formato JSON (para a estensão fazer a leitura)
  }
 
  delay(1000);

}

// Funçao que informa o estado do LED via serial em formato JSON (para a estensão fazer a leitura)
void printLEDStatus () {
    bool ledStatus = digitalRead(LED); // Lê o estado atual do LED
   
    String json = "{"ledStatus": " + String(ledStatus) + "}"; // Cria o JSON para enviar

    Serial.println(json); // Envia o JSON por serial
}

Se você ler com calma e entender, vai reparar que não é muito complicado de modificar o código para a sua aplicação desejada. Veja o curso de Arduino do site, que você vai ter uma boa base.

Para ver o código funcionando, apenas faça upload e veja como usar a extensão abaixo.

Como usar

Em versões mais recentes do Chrome, a comunicação serial começou a apresentar problemas. Então, para a extensão funcionar, é necessário abrir o Google Chrome no modo de administrador.

Agora, acesse a página ‘chrome://apps/’ e clique na extensão e a seguinte tela irá aparecer:

Extensão Reconhecimento de Voz

Temos 4 elementos importantes:

  • Botão conectar e barra de conexões: Se você estiver com o Arduino conectado ao computador, a barra que fica ao lado do botão conectar irá mostrar um valor. Então, você deve escolher a porta e clicar em conectar. Com isso, a extensão estará pronta para mandar dados ao Arduino.
  • Botão Falar: Ao clicar, você habilita o reconhecimento de voz. O programa começa a reconhecer a sua voz até que tenha um momento de silêncio. E com isso, a frase reconhecida fica fixada abaixo da “barra de conexões”. Na imagem acima, primeiro eu falei “testando 1 2 3” e depois eu falei “mundo projetado”. O programa só para de fixar as frases se você clicar no botão de novo e desabilitar o reconhecimento.
  • Barra central: a parte branca que fica no meio apenas mostra o que está sendo reconhecido (voz) pelo programa.
  • Botão Led e circulo roxo: O circulo roxo indica o estado do Led da programação do Arduino. Quando o Arduino está conectado, o circulo roxo muda a cor para verde ou vermelho, dependendo do estado do LED (pino 13). O botão Led serve para acionar o Led manualmente e testar a comunicação serial.

Existe um comando existente que configurei, que é o comando “horas”. Não preciso nem mencionar o que ele faz.

Para modificar o programa e saber o que faz cada arquivo acompanhe abaixo:

Obs.: O arquivo jquery-1.11.0.min é uma espécie de biblioteca de javascript.

Manifest.json

Arquivo manifest

O que temos de importante nesse arquivo é:

  • Permissions: permissões que o aplicativo utiliza. No caso, a comunicação serial e a captura de áudio. Sem essas permissões, o programa não ia conseguir gravar o áudio do microfone e nem enviar dados por serial
  • icons: tamanho e nome do arquivo do ícone da extensão. No caso, o nome do arquivo é icone.png mesmo
  • background: o script de inicialização do programa

Background.js

Arquivo background

Como dito anteriormente, esse é o script de inicialização do programa. Basicamente define o html responsável pela extensão e o tamanho da janela (720×480).

INDEX.html

Arquivo index

Esse arquivo é responsável, principalmente, pela aparência do programa. Na imagem acima, tudo que está acima de <body> são, basicamente, configurações do visual dos botões, caixas de texto e do titulo.

Então não é necessário comentar sobre. Quem quiser entender 100%, basta aprender HTML. O que tem de importante a ser mencionado é a linha que inicializa o script responsável pelas funções do programa (

Main.js

Esse é o arquivo responsável por criar todas as funções da extensão: reconhecimento de voz, comunicação serial, mudar a cor do círculo etc. Os comentários em inglês são os do Fabio Biondi, autor do script original.

Com minhas alterações, eu adicionei comentários em português para facilitar a compreensão de algumas partes. Não precisa entender 100% do código, apenas o essencial. Vamos as partes importantes então:

Comunicação Serial

Arquivo main comunicação serial

A função acima é a que controla o botão Led. Basicamente se o botão for pressionado, a função é acionada e ela entra em um if “se conectado”. A variável conectado indica se a pessoa conectou o Arduino (clicou no botão conectar).

Com isso, o código comuta o valor da variável is_on (se era true vira false e vice-versa). E por fim, usa o comando connection.send. Comando este, que envia alguma informação via Serial.

Neste caso, o programa envia ‘y’ se a variável is_on for Verdadeira e ‘n’ se for Falsa. Essa é a tradução do que a interrogação (?) está fazendo. É importante entender essa função, para saber como enviar dados para o Arduino e criar seu próprio programa.

Reconhecimento de voz

Arquivo Main função reconhecimento

A função completa pode ser dificil de entender a princípio. Porém a parte importante está circulada em vermelho. É naquela área do programa que você deve inserir novos comandos para serem reconhecidos. 

transcript.indexOf(‘horas’) basicamente retorna o índice da palavra ‘horas’ na frase que foi reconhecida. Esse processo é feito depois que o usuário terminou de falar e a frase já foi reconhecida.

Obs.: Existe uma função horas() que eu criei, que retorna o valor das horas no formato: São x hora(s) y minuto(s) e z segundo(s).

Portanto, se o índice da palavra horas for maior que -1, isso indica que aquela palavra existe na frase reconhecida. Com isso, eu reconheço que o usuário quer saber as horas e faço duas coisas: fixa as horas na parte do programa que fica abaixo da “barra de conexões” com log(horas()). Log é uma função que existe nesse código para poder fixar a escrita na área que eu mencionei.

E, por fim, o programa cria uma síntese de fala com a frase da função horas. Sendo assim, o comando window.speechSynthesis.speak(new SpeechSynthesisUtterance(“FRASE DESEJADA”)); manda o computador falar a frase desejada.

Agora, para criar seus próprios comandos, basta colocar outro if abaixo e usar a mesma lógica: transcript.indexOf(‘PALAVRA DESEJADA’) tem que ser maior que -1. Com isso você pode combinar com a função connection.send descrita acima.

 

Comentários finais

De modo geral, essa solução é muito interessante e legal de usar. Gastei um tempo enorme para conseguir chegar no resultado apresentado. Então espero que seja bem aproveitado e útil para você.

Reconhecimento de voz – Como fazer?