问题
I have a form and I want to allow the user to receive asynchronous text-to-speech output based on the content of a text box whenever a button is pressed. For context, this form is launched as part of an "internal" C# function within VoiceAttack, and this is a continuation of a previous question. This snippet does the job nicely:
SpeechSynthesizer synth = new SpeechSynthesizer(); // Create new SpeechSynthesizer instance
// Function for asynchronous voicing of text with text-to-speech
public void VoiceText(string text)
{
string MyVoice = null; // Initialize string for storing requested text-to-speech voice
string DefaultVoice = null; // Initialize string for storing default Windows text-to-speech voice
try // Attempt the following code...
{
synth.SpeakAsyncCancelAll(); // Cancels all queued, asynchronous, speech synthesis operations
synth.Volume = 100; // Set the volume level of the text-to-speech voice
synth.Rate = -2; // Set the rate at which text is spoken by the text-to-speech engine
MyVoice = VA.GetText(">SDTTextToSpeechVoice") ?? "Not Set"; // Retrieve phonemes for processed text or set to null
DefaultVoice = synth.Voice.Name; // Store the current default Windows text-to-speech voice
if (MyVoice == "Default") // Check if requested voice name is "Default"
{
MyVoice = DefaultVoice; // Set MyVoice to the DefaultVoice
VA.SetText(">SDTTextToSpeechVoice", MyVoice); // Redefine VoiceAttack text variable based on redefined MyVoice
}
synth.SelectVoice(MyVoice); // Set the voice for this instance of text-to-speech output
}
catch // Handle exceptions encountered in "try"
{
synth.SelectVoice(DefaultVoice); // Set the voice for this instance of text-to-speech output to the Windows default voice
string VoiceList = null; // Initialize string variable for storing available text-to-speech voice names
foreach (InstalledVoice v in synth.GetInstalledVoices()) // Loop through all available text-to-speech voices
VoiceList += ", " + v.VoiceInfo.Name; // Add text-to-speech voice name to storage variable
VA.WriteToLog("Text-to-speech voice '" + MyVoice + "' not found", "yellow"); // Output info to event log
VA.WriteToLog("Valid TTS Voices = " + VoiceList.Trim(',', ' '), "yellow"); // Output info to event log
VA.WriteToLog("Defaulting to current Windows text-to-speech voice (" + DefaultVoice + ")", "yellow"); // Output info to event log
}
synth.SpeakAsync(text); // Generate text-to-speech output asynchronously
}
// Function for disposing SpeechSynthesizer object
public void SpeechDispose()
{
synth.Dispose(); // Releases resources tied to SpeechSynthesizer object
}
SpeechDispose()
is called upon form closing. I can't enclose synth in a using()
statement because the voicing is asynchronous (I want the user to not be forced to wait for the voicing to finish before the button can be pressed again). Is there a better way to clean up?
来源:https://stackoverflow.com/questions/55168576/how-to-properly-dispose-of-speechsynthesizer-for-async-text-to-speech