Riconoscimento vocale

Usare il riconoscimento vocale per fornire input, specificare un'azione o un comando ed eseguire attività.

API importanti: Windows.Media.SpeechRecognition

Il riconoscimento vocale è costituito da un runtime di riconoscimento vocale, api di riconoscimento per la programmazione del runtime, grammatiche pronte per l'uso per la dettatura e la ricerca web e un'interfaccia utente di sistema predefinita che consente agli utenti di individuare e usare le funzionalità di riconoscimento vocale.

Configurare il riconoscimento vocale

Per supportare il riconoscimento vocale all'interno dell'app, l'utente deve connettersi e abilitare un microfono nel dispositivo e accettare l'informativa sulla privacy di Microsoft concedendo l'autorizzazione per l'uso dell'app.

Per richiedere automaticamente all'utente un dialogo di sistema che richiede l'autorizzazione per accedere e usare il feed audio del microfono (ad esempio dall'esempio di riconoscimento vocale e sintesi vocale illustrato di seguito), è sufficiente impostare la funzionalità del dispositivo Microfono nel manifesto del pacchetto dell'app. Per ulteriori informazioni, vedere Dichiarazioni di funzionalità dell'app.

Informativa sulla privacy per l'accesso al microfono

Se l'utente fa clic su Sì per concedere l'accesso al microfono, l'app viene aggiunta all'elenco delle applicazioni approvate nella pagina Impostazioni -> Privacy -> Microfono. Tuttavia, poiché l'utente può scegliere di disattivare questa impostazione in qualsiasi momento, è necessario verificare che l'app abbia accesso al microfono prima di tentare di usarlo.

Se si desidera supportare anche la dettatura, Cortana o altri servizi di riconoscimento vocale (ad esempio una grammatica predefinita definita in un vincolo di argomento), è necessario anche verificare che sia abilitato il Riconoscimento vocale online (Impostazioni -> Privacy -> Riconoscimento vocale).

Questo frammento di codice mostra come l'app può verificare se è presente un microfono e se dispone dell'autorizzazione per usarlo.

public class AudioCapturePermissions
{
    // If no microphone is present, an exception is thrown with the following HResult value.
    private static int NoCaptureDevicesHResult = -1072845856;

    /// <summary>
    /// Note that this method only checks the Settings->Privacy->Microphone setting, it does not handle
    /// the Cortana/Dictation privacy check.
    ///
    /// You should perform this check every time the app gets focus, in case the user has changed
    /// the setting while the app was suspended or not in focus.
    /// </summary>
    /// <returns>True, if the microphone is available.</returns>
    public async static Task<bool> RequestMicrophonePermission()
    {
        try
        {
            // Request access to the audio capture device.
            MediaCaptureInitializationSettings settings = new MediaCaptureInitializationSettings();
            settings.StreamingCaptureMode = StreamingCaptureMode.Audio;
            settings.MediaCategory = MediaCategory.Speech;
            MediaCapture capture = new MediaCapture();

            await capture.InitializeAsync(settings);
        }
        catch (TypeLoadException)
        {
            // Thrown when a media player is not available.
            var messageDialog = new Windows.UI.Popups.MessageDialog("Media player components are unavailable.");
            await messageDialog.ShowAsync();
            return false;
        }
        catch (UnauthorizedAccessException)
        {
            // Thrown when permission to use the audio capture device is denied.
            // If this occurs, show an error or disable recognition functionality.
            return false;
        }
        catch (Exception exception)
        {
            // Thrown when an audio capture device is not present.
            if (exception.HResult == NoCaptureDevicesHResult)
            {
                var messageDialog = new Windows.UI.Popups.MessageDialog("No Audio Capture devices are present on this system.");
                await messageDialog.ShowAsync();
                return false;
            }
            else
            {
                throw;
            }
        }
        return true;
    }
}
/// <summary>
/// Note that this method only checks the Settings->Privacy->Microphone setting, it does not handle
/// the Cortana/Dictation privacy check.
///
/// You should perform this check every time the app gets focus, in case the user has changed
/// the setting while the app was suspended or not in focus.
/// </summary>
/// <returns>True, if the microphone is available.</returns>
IAsyncOperation<bool>^  AudioCapturePermissions::RequestMicrophonePermissionAsync()
{
    return create_async([]() 
    {
        try
        {
            // Request access to the audio capture device.
            MediaCaptureInitializationSettings^ settings = ref new MediaCaptureInitializationSettings();
            settings->StreamingCaptureMode = StreamingCaptureMode::Audio;
            settings->MediaCategory = MediaCategory::Speech;
            MediaCapture^ capture = ref new MediaCapture();

            return create_task(capture->InitializeAsync(settings))
                .then([](task<void> previousTask) -> bool
            {
                try
                {
                    previousTask.get();
                }
                catch (AccessDeniedException^)
                {
                    // Thrown when permission to use the audio capture device is denied.
                    // If this occurs, show an error or disable recognition functionality.
                    return false;
                }
                catch (Exception^ exception)
                {
                    // Thrown when an audio capture device is not present.
                    if (exception->HResult == AudioCapturePermissions::NoCaptureDevicesHResult)
                    {
                        auto messageDialog = ref new Windows::UI::Popups::MessageDialog("No Audio Capture devices are present on this system.");
                        create_task(messageDialog->ShowAsync());
                        return false;
                    }

                    throw;
                }
                return true;
            });
        }
        catch (Platform::ClassNotRegisteredException^ ex)
        {
            // Thrown when a media player is not available. 
            auto messageDialog = ref new Windows::UI::Popups::MessageDialog("Media Player Components unavailable.");
            create_task(messageDialog->ShowAsync());
            return create_task([] {return false; });
        }
    });
}
var AudioCapturePermissions = WinJS.Class.define(
    function () { }, {},
    {
        requestMicrophonePermission: function () {
            /// <summary>
            /// Note that this method only checks the Settings->Privacy->Microphone setting, it does not handle
            /// the Cortana/Dictation privacy check.
            ///
            /// You should perform this check every time the app gets focus, in case the user has changed
            /// the setting while the app was suspended or not in focus.
            /// </summary>
            /// <returns>True, if the microphone is available.</returns>
            return new WinJS.Promise(function (completed, error) {

                try {
                    // Request access to the audio capture device.
                    var captureSettings = new Windows.Media.Capture.MediaCaptureInitializationSettings();
                    captureSettings.streamingCaptureMode = Windows.Media.Capture.StreamingCaptureMode.audio;
                    captureSettings.mediaCategory = Windows.Media.Capture.MediaCategory.speech;

                    var capture = new Windows.Media.Capture.MediaCapture();
                    capture.initializeAsync(captureSettings).then(function () {
                        completed(true);
                    },
                    function (error) {
                        // Audio Capture can fail to initialize if there's no audio devices on the system, or if
                        // the user has disabled permission to access the microphone in the Privacy settings.
                        if (error.number == -2147024891) { // Access denied (microphone disabled in settings)
                            completed(false);
                        } else if (error.number == -1072845856) { // No recording device present.
                            var messageDialog = new Windows.UI.Popups.MessageDialog("No Audio Capture devices are present on this system.");
                            messageDialog.showAsync();
                            completed(false);
                        } else {
                            error(error);
                        }
                    });
                } catch (exception) {
                    if (exception.number == -2147221164) { // REGDB_E_CLASSNOTREG
                        var messageDialog = new Windows.UI.Popups.MessageDialog("Media Player components not available on this system.");
                        messageDialog.showAsync();
                        return false;
                    }
                }
            });
        }
    })

Riconoscimento di un input vocale

Un vincolo definisce le parole e le frasi (vocabolario) riconosciute da un'app nell'input vocale. I vincoli sono essenziali per il riconoscimento vocale e offrono all'app un maggiore controllo sull'accuratezza di tale riconoscimento.

Per il riconoscimento dell'input vocale è possibile usare i tipi di vincoli seguenti.

Grammatiche predefinite

Le grammatiche predefinite per la dettatura e la ricerca web forniscono il riconoscimento vocale per l'app senza che sia necessario creare una grammatica. Quando si usano queste grammatiche, il riconoscimento vocale viene eseguito da un servizio web remoto e i risultati vengono restituiti al dispositivo.

La grammatica di dettatura a testo libero predefinita può riconoscere la maggior parte delle parole e frasi che un utente può pronunciare in una determinata lingua ed è ottimizzata per riconoscere frasi brevi. Se non si specificano vincoli per l'oggetto SpeechRecognizer viene utilizzata la grammatica di dettatura predefinita. La dettatura a testo libero è utile quando non si desidera limitare i tipi di elementi che un utente può pronunciare. Gli usi tipici includono la creazione di note o la dettatura del contenuto di un messaggio.

La grammatica per la ricerca web, ad esempio una grammatica di dettatura, contiene un numero elevato di parole e frasi che un utente potrebbe pronunciare. Tuttavia, è ottimizzata per riconoscere i termini che le persone usano in genere durante la ricerca nel web.

Nota

 Poiché le grammatiche di dettatura e per la ricerca web predefinite possono essere di grandi dimensioni e poiché sono online (non sul dispositivo), le prestazioni potrebbero non essere veloci quanto quelle che prevedono l'utilizzo di una grammatica personalizzata installata sul dispositivo.  

Queste grammatiche predefinite possono essere usate per riconoscere fino a 10 secondi di input vocale e non richiedono alcuna attività di creazione da parte dell'utente. Tuttavia, richiedono una connessione a una rete.

Per usare i vincoli del servizio web, è necessario abilitare l'input vocale e il supporto della dettatura in Impostazioni attivando l'opzione "Ottieni informazioni" in Impostazioni -> Privacy -> Riconoscimento vocale, input penna e digitazione.

In questo articolo viene illustrato come verificare se l'input vocale è abilitato e aprire la pagina Impostazioni -> Privacy -> Riconoscimento vocale, input penna e digitazione, in caso contrario.

In primo luogo, si inizializza una variabile globale (HResultPrivacyStatementDeclined) al valore HResult di 0x80045509. Vedere Gestione delle eccezioni in C# o Visual Basic.

private static uint HResultPrivacyStatementDeclined = 0x80045509;

Vengono quindi rilevate eccezioni standard durante il riconoscimento e si verifica se il valore HResult è uguale al valore della variabile HResultPrivacyStatementDeclin. In questo caso, viene visualizzato un avviso e viene chiamato await Windows.System.Launcher.LaunchUriAsync(new Uri("ms-settings:privacy-accounts")); per aprire la pagina Impostazioni.

catch (Exception exception)
{
  // Handle the speech privacy policy error.
  if ((uint)exception.HResult == HResultPrivacyStatementDeclined)
  {
    resultTextBlock.Visibility = Visibility.Visible;
    resultTextBlock.Text = "The privacy statement was declined." + 
      "Go to Settings -> Privacy -> Speech, inking and typing, and ensure you" +
      "have viewed the privacy policy, and 'Get To Know You' is enabled.";
    // Open the privacy/speech, inking, and typing settings page.
    await Windows.System.Launcher.LaunchUriAsync(new Uri("ms-settings:privacy-accounts")); 
  }
  else
  {
    var messageDialog = new Windows.UI.Popups.MessageDialog(exception.Message, "Exception");
    await messageDialog.ShowAsync();
  }
}

Vedere SpeechRecognitionTopicConstraint.

Vincoli di elenco a livello di codice

I vincoli di elenco a livello di codice offrono un approccio facilitato alla creazione di grammatiche semplici usando un elenco di parole o frasi. Un vincolo di elenco funziona bene per il riconoscimento di frasi brevi e distinte. Specificare esplicitamente tutte le parole in una grammatica migliora anche l'accuratezza del riconoscimento, poiché il motore di riconoscimento vocale deve elaborare il riconoscimento vocale solo per confermare una corrispondenza. L'elenco può anche essere aggiornato a livello di codice.

Un vincolo di elenco è costituito da una matrice di stringhe che rappresenta l'input vocale che l'app accetterà per un'operazione di riconoscimento. È possibile creare un vincolo di elenco nell'app creando un oggetto list-constraint di riconoscimento vocale e passando una matrice di stringhe. Aggiungere quindi l'oggetto alla raccolta di vincoli del riconoscitore. Il riconoscimento ha esito positivo quando il riconoscimento vocale riconosce una delle stringhe nella matrice.

Vedere SpeechRecognitionListConstraint.

Grammatiche SRGS

Una grammatica SRGS (Speech Recognition Grammar Specification) è un documento statico che, a differenza di un vincolo di elenco programmatico, usa il formato XML definito da SRGS versione 1.0. Una grammatica SRGS offre il massimo controllo sull'esperienza di riconoscimento vocale consentendo di acquisire più significati semantici in un singolo riconoscimento.

Vedere SpeechRecognitionGrammarFileConstraint.

Vincoli dei comandi vocali

Usare un file XML VCD (Voice Command Definition) per definire i comandi che l'utente può pronunciare per avviare azioni durante l'attivazione dell'app. Per altri dettagli, vedere Attivare un'app in primo piano con comandi vocali tramite Cortana.

Vedere SpeechRecognitionVoiceCommandDefinitionConstraint/

Nota Il tipo di vincolo usato dipende dalla complessità dell'esperienza di riconoscimento che si desidera creare. Ognuna di queste potrebbe essere la scelta migliore per un'attività di riconoscimento specifica ed è possibile trovare usi per tutti i tipi di vincoli nell'app. Per iniziare a usare i vincoli, vedere Definire vincoli di riconoscimento personalizzati.

La grammatica di dettatura dell'app di Windows universale predefinita riconosce la maggior parte delle parole e delle frasi brevi in una lingua. Viene attivata per impostazione predefinita quando viene creata un'istanza di un oggetto riconoscimento vocale senza vincoli personalizzati.

In questo esempio viene illustrato come:

  • Creare un riconoscimento vocale.
  • Compilare i vincoli predefiniti delle app di Windows universali (senza l'aggiunta di alcuna grammatica al set di grammatiche del riconoscimento vocale).
  • Iniziare ad ascoltare il parlato usando l'interfaccia utente di riconoscimento di base e il feedback TTS forniti dal metodo RecognizeWithUIAsync. Usare il metodo RecognizeAsync se l'interfaccia utente predefinita non è necessaria.
private async void StartRecognizing_Click(object sender, RoutedEventArgs e)
{
    // Create an instance of SpeechRecognizer.
    var speechRecognizer = new Windows.Media.SpeechRecognition.SpeechRecognizer();

    // Compile the dictation grammar by default.
    await speechRecognizer.CompileConstraintsAsync();

    // Start recognition.
    Windows.Media.SpeechRecognition.SpeechRecognitionResult speechRecognitionResult = await speechRecognizer.RecognizeWithUIAsync();

    // Do something with the recognition result.
    var messageDialog = new Windows.UI.Popups.MessageDialog(speechRecognitionResult.Text, "Text spoken");
    await messageDialog.ShowAsync();
}

Personalizzare l'interfaccia utente di riconoscimento

Quando l'app tenta il riconoscimento vocale chiamando SpeechRecognizer.RecognizeWithUIAsync, vengono visualizzate diverse schermate nell'ordine seguente.

Se si usa un vincolo basato su una grammatica predefinita (dettatura o ricerca web):

  • La schermata di Ascolto.
  • La schermata di Elaborazione.
  • La schermata Ti ho sentito dire o la schermata di errore.

Se si usa un vincolo basato su un elenco di parole o frasi o un vincolo basato su un file di grammatica SRGS:

  • La schermata di Ascolto.
  • La schermata Hai detto, se ciò che l'utente ha detto potrebbe essere interpretato come più di un risultato potenziale.
  • La schermata Ti ho sentito dire o la schermata di errore.

L'immagine seguente mostra un esempio del flusso tra le schermate per un riconoscimento vocale che usa un vincolo basato su un file di grammatica SRGS. In questo esempio il riconoscimento vocale ha avuto esito positivo.

schermata di riconoscimento iniziale per un vincolo basato su un file di grammatica sgrs

schermata di riconoscimento intermedio per un vincolo basato su un file di grammatica sgrs

schermata di riconoscimento finale per un vincolo basato su un file di grammatica sgrs

La schermata Ascolto può fornire esempi di parole o frasi che l'app riesce a riconoscere. Qui viene illustrato come usare le proprietà della classe SpeechRecognizerUIOptions (ottenuta chiamando la proprietà SpeechRecognizer.UIOptions) per personalizzare il contenuto nella schermata Ascolto.

private async void WeatherSearch_Click(object sender, RoutedEventArgs e)
{
    // Create an instance of SpeechRecognizer.
    var speechRecognizer = new Windows.Media.SpeechRecognition.SpeechRecognizer();

    // Listen for audio input issues.
    speechRecognizer.RecognitionQualityDegrading += speechRecognizer_RecognitionQualityDegrading;

    // Add a web search grammar to the recognizer.
    var webSearchGrammar = new Windows.Media.SpeechRecognition.SpeechRecognitionTopicConstraint(Windows.Media.SpeechRecognition.SpeechRecognitionScenario.WebSearch, "webSearch");


    speechRecognizer.UIOptions.AudiblePrompt = "Say what you want to search for...";
    speechRecognizer.UIOptions.ExampleText = @"Ex. 'weather for London'";
    speechRecognizer.Constraints.Add(webSearchGrammar);

    // Compile the constraint.
    await speechRecognizer.CompileConstraintsAsync();

    // Start recognition.
    Windows.Media.SpeechRecognition.SpeechRecognitionResult speechRecognitionResult = await speechRecognizer.RecognizeWithUIAsync();
    //await speechRecognizer.RecognizeWithUIAsync();

    // Do something with the recognition result.
    var messageDialog = new Windows.UI.Popups.MessageDialog(speechRecognitionResult.Text, "Text spoken");
    await messageDialog.ShowAsync();
}

Esempi