如何播放音频样本而不将其写入文件?

Posted

技术标签:

【中文标题】如何播放音频样本而不将其写入文件?【英文标题】:How to play audio samples without writing it into to a file? 【发布时间】:2021-02-04 09:27:09 【问题描述】:

我从另一种方法获取音频样本(作为浮点数组) 我想在不将任何文件写入磁盘的情况下播放这个浮点数组。

对于这个例子,我从音频文件中获取样本:

var file = new AudioFileReader(stereoFile);

int startPos = 0;
int endPos = 138890;

var sampleArray = new float[endPos - startPos];

file.Read(sampleArray, startPos, sampleArray.Length);

如何玩sampleArray

【问题讨论】:

这能回答你的问题吗? How can I play byte array of audio raw data using NAudio? @00110001 这是字节数组,而不是浮点样本数组。此答案不适用于示例 @Sinatr 很遗憾没有。 Sinatr 的答案应该在您将这些浮点样本转换为例如16 位签名样本。 @AKX 这是可能的方式,但如果我正确理解这个问题***.com/questions/18689410/… 这种方式并不容易。也许有更好的方法来做到这一点? 【参考方案1】:

我找到了下一个解决方案,它对我有用:

        var file = new AudioFileReader(stereoFile);

        WaveFormat waveFormat = file.WaveFormat;

        int startPos = 2403;
        int endPos = 41265;

        if (startPos % 2 != 0)
        
            startPos += 1;
        

        if (endPos % 2 != 0)
        
            endPos += 1;
        

        if (waveFormat.Channels == 2)
        
            startPos *= 2;
            endPos *= 2;
        

        var allSamples = new float[file.Length / (file.WaveFormat.BitsPerSample / 8)];

        file.Read(allSamples, 0, allSamples.Length);

        Span<float> samplesSpan = allSamples;
        Span<float> trackSpan = samplesSpan.Slice(startPos, endPos - startPos);

^ 上层代码以获取正确的样本进行测试。 下面的代码 - 我的解决方案

        MemoryStream ms = new MemoryStream();
        IgnoreDisposeStream ids = new IgnoreDisposeStream(ms);

        using (WaveFileWriter waveFileWriter = new WaveFileWriter(ids, waveFormat))
        
            waveFileWriter.WriteSamples(trackSpan.ToArray(), 0, endPos-startPos);
        


        ms.Position = 0;
        WaveStream waveStream = new WaveFileReader(ms);
        WaveOutEvent waveOutEvent = new WaveOutEvent();
        waveOutEvent.Init(waveStream);
        waveOutEvent.Play();

【讨论】:

【参考方案2】:

RawSourceWaveStream 专为您在字节数组或MemoryStream 中有音频并希望直接播放的情况而设计。您可以了解更多信息并查看如何使用它的示例here

【讨论】:

如何使用 RawSourceWaveStream 播放示例数组? RawSourceWaveStream 可以使用 byte[] 或 Stream 但不能使用 float[] 您可以使用 WaveBuffer 类作为在两者之间进行转换的一种方式,或者使用 Buffer.BlockCopy 之类的东西将浮点样本复制到一个字节[]

以上是关于如何播放音频样本而不将其写入文件?的主要内容,如果未能解决你的问题,请参考以下文章

如何在现有 csv 文件中写入新行而不将其附加到最后一行?

从python内存中的MPEG(.ts)文件中提取音频,而不将MPEG写入文件

如何处理来自 WASAPI 流的声音数据块而不将它们写入文件?

如何将嵌入式资源作为字节数组读取而不将其写入磁盘?

如何在 MYSQL 中运行查询而不将其写入二进制日志

使用 keytab 而不将其写入磁盘的 Bash 脚本