0

I am using the SpeechSynthesizer class in a C# asp.net app to attempt to convert some text to speech and then write that audio memory stream out to the response so it can be downloaded as a .wav by the end user.

I can save the memorystream to a filestream and the wav plays fine (tested this in a seperate function) however when trying to send a memorystream to the response (code below) it looks like IE says the .wav file is being downloaded however it is almost like something is hanging on to the object and won't let it complete downloading. The .wav as a result can not be opened to play the sound.

Any thoughts on how to properly do this? Here is my code below.

        SpeechSynthesizer synth = new SpeechSynthesizer();
        MemoryStream streamAudio = new MemoryStream();

        // Configure the synthesizer to output to an audio stream.
        synth.SetOutputToWaveStream(streamAudio);

        // Speak a phrase.
        synth.Speak("This is sample text-to-speech output.");

        // Set audio stream to beginning
        streamAudio.Position = 0;

        // Send the memory steam bytes out to the response/
        Response.Clear();
        Response.ContentType = "audio/wav";
        Response.AppendHeader("Content-Disposition", "attachment; filename=mergedoutput.wav");
        streamAudio.CopyTo(Response.OutputStream);
        Response.Flush();
        Response.End();
Al Belmondo
  • 764
  • 10
  • 26

2 Answers2

0

Found the solution... The speak method needs to run in its own thread and then return the byte array that can be witten to the response.

Found the solution in this post

C# SpeechSynthesizer makes service unresponsive

Community
  • 1
  • 1
Al Belmondo
  • 764
  • 10
  • 26
0

My code works well in .NET Core

/// <summary>
/// 使用windows生成声音
/// </summary>
/// <param name="text"></param>
/// <returns></returns>
private async Task<byte[]> GetAudioByWindows(string text)
{
    using (var synth = new SpeechSynthesizer())
    {
        var streamAudio = new MemoryStream();

        synth.SetOutputToWaveStream(streamAudio);
        synth.Speak(text);

        //using (var fileStream = System.IO.File.Create(path))
        //{
        //    streamAudio.Seek(0, SeekOrigin.Begin);
        //    streamAudio.CopyTo(fileStream);
        //}
        streamAudio.Position = 0;
        synth.SetOutputToNull();

        return streamAudio.ToArray();
        //if need reduce size return this
        //return await ConvertToMp3Async(streamAudio);
    }
}
/// <summary>
/// 将wave格式音频转为mp3
/// </summary>
/// <param name="wave"></param>
/// <returns></returns>
public async Task<byte[]> ConvertToMp3Async(Stream wave)
{
    //using NAudio.Lame;
    var target = new WaveFormat(8000, 16, 1);
    using (var outPutStream = new MemoryStream())
    using (var waveStream = new WaveFileReader(wave))
    using (var conversionStream = new WaveFormatConversionStream(target, waveStream))
    using (var writer = new LameMP3FileWriter(outPutStream, conversionStream.WaveFormat, 16, null))
    {
        await conversionStream.CopyToAsync(writer);

        return outPutStream.ToArray();
    }
}

use return File(GetAudioByWindows(text), "audio/mp3") to return audio in controller.

我零0七
  • 315
  • 3
  • 6