[#wpdev] Speech API: il riconoscimento vocale

Nell’ultimo post, abbiamo parlato del componente delle Speech API che ci permette di far “leggere” del testo alle nostre applicazioni: il text to speech. In questo post, vedremo il terzo pilastro di queste API ovvero il riconoscimento vocale.

Lo scopo di questo “mattone”, come è facile da intuire, quello di tradurre l’input vocale recepito dal microfono in testo scritto, utilizzabile nelle nostre applicazioni. Per via della complessità insita nella procedura di riconoscimento vocale, il lavoro di “traduzione” viene eseguito sul cloud da server dedicati allo scopo. La scelta di questa modalità, condivisibile o meno,  è dettata da due fattori fondamentali:

  1. precisione: tradurre correttamente la voce in testo è una operazione estremamente complessa e onerosa. Sebbene l’hardware dei nostri smartphone sia di tutto rispetto, un accurato riconoscimento vocale richiede macchine decisamente più potenti
  2. velocità: il riconoscimento deve essere una operazione veloce, soprattutto in scenari di in-app dialog. L’hardware degli smartphone attuali (e non solo Windows Phone), non può garantire estrema precisione e velocità di elaborazione in questi contesti specifici

A questi due fattori, si aggiunge un terzo elemento tutt’altro che trascurabile: la durata della batteria. E’ ovvio che più capacità di calcolo chiediamo al processore, maggiore sarà il consumo energetico e minore sarà la durata della batteria. L’elaborazione on line unisce, di fatto, precisione e velocità nel riconoscimento ed un dispendio energetico molto modesto.

Ovviamente, non saremo noi ad occuparci dello scambio dati tra il nostro dispositivo ed i server di riconoscimento vocale. A fare tutto il lavoro se ne occupa l’oggetto SpeechRecognizerUI. Una volta configurato ed istanziato, sarà sufficiente richiamare il metodo RecognizeWithUIAsync per avviare il processo di riconoscimento attraverso l’interfaccia utente a cui siamo ormai abituati.

La configurabilità di questo componente è relativa ad alcuni aspetti della UI di riconoscimento e del comportamento del riconoscitore. Nello specifico:

ListenText definisce il messaggio da visualizzare nell’interfaccia di riconoscimento vocale (ad esempio: detta la tua nota)
ExampleText è il classico testo di esempio da mostrare all’utente
ReadoutEnabled se impostato a true, il testo riconosciuto verrà riletto dal sistema. E’ molto utile per dare un feedback all’utente che, molto probabilmente, non stà guardando il display del dispositivo
ShowConfirmation mostra l’eventuale conferma di avvenuto riconoscimento. Se impostato a false, il testo riconosciuto non verrà riletto

 

Una volta avviato il riconoscitore, non ci resta che gestire il risultato. Esso sarà contenuto in un oggetto di tipo SpeechRecognitionUIResult al cui interno, oltre al testo riconosciuto, troveremo altre informazioni come il livello di confidence.

Dal punto di vista del codice, il tutto si traduce in poche righe di codice:

27-03-2013 16.30

Il livello di confidence, accessibile dalla property result.RecognitionResult.TextConfidence, può avere i valori High, Medium, Low e Rejected e può essere utile a gestire eventuali interazioni in caso di riconoscimento “incerto”. Nell’eventualità il livello di confidence sia diverso da High, abbiamo la possibilità di recuperare una serie di alternative attraverso il metodo GetAlternates().

L’utilizzo della UI in fase di riconoscimento, sebbene sia molto comodo ed utile, diventa scomodo e di intralcio quando, ad esempio, dobbiamo gestire eventuali comandi. Pensiamo alla nostra applicazione per prendere appunti: se per riconoscere il comando di salvataggio o di annullamento dobbiamo scomodare tutto il flusso del riconoscimento vocale (cloud compreso), l’applicazione diventerebbe inusabile. Per ovviare a questo problema, è stato introdotto il concetto di Speech Recognition Grammar. Grazie ad esso, abbiamo la possibilità di creare un set limitato di parole che verranno riconosciute localmente (quindi senza scomodare il cloud) e senza la necessità di utilizzare la UI. Lo scenario tipico è appunto quello di poter definire dei comandi o delle parole chiave per compiere action specifiche nella nostra applicazione.

Anche l’utilizzo delle custom grammar è molto semplice: innanzitutto definiamo e registriamo i nostri comandi in questo modo:

27-03-2013 16.52

Quando dobbiamo utilizzarli, sarà sufficiente usare l’oggetto  RecognizeAsync() che, come il RecognizeUIAsync visto in precedenza, restituirà il testo riconosciuto che poi potremmo gestire:

27-03-2013 16.53

Ora che abbiamo tutti gli elementi, non ci resta che impostare il vero e proprio “in app dialog”, che vedremo nel prossimo post.

,