【发布时间】:2011-12-23 22:26:55
【问题描述】:
我正在尝试输出音频样本,并使用来自http://www.codeproject.com/KB/audio-video/cswavplay.aspx 的 cswavplay 执行此操作,而后者似乎使用来自 winmm.dll 的DllImports。
我确实让它使用 8 位样本播放,但是当我尝试向它提供 16 位样本时它惨遭失败。我尽可能地挖掘了代码,我的理解是这样的:
每次 cswavplay 播放完最后一个缓冲区时,我都会获得一个指向缓冲区的指针。它适用于一次迭代,它播放一个缓冲区,有时...... 我得到了各种有趣的异常,例如,当我尝试使用 44100 的缓冲区大小来更清楚地听到播放了多少时,AccessViolationException 刚刚发生。但是,当我在 WaveOut 类(cswavplay 的一部分)内的不同位置放置断点时,似乎它使用的所有对象(如缓冲区和 AutoResetEvent 的实例)在第二次迭代中仍然存在。我最好的猜测是这些问题与线程或 GC 有关。异常似乎很随机,而且我经验不足,无法完全理解发生了什么。
我要求以下任何一项:
1) 胡乱猜测可能是什么问题
2) 有根据的猜测可能是什么问题
3) 指向使用 C# 实时输出声音的另一种方法
我并不是要求对不是我编写的软件进行彻底的错误跟踪,所以不要介意 cswavplay...
归根结底,我可能在这里做错了什么,但很难知道我什么时候没有得到相关的异常(沿着BufferAllocationException 或其他东西的行)...
编辑:
感谢您对其他声音 API 的所有建议。他们似乎都假设一个 .wav 文件。很抱歉没有说清楚,我不是在播放 .wav 文件,我是实时合成样本。
【问题讨论】:
-
GC。不要这么想。穿线?也许,你使用线程吗?
-
我只能提供 (II),但是在 16-bit-per-sample 操作中使用 8-bit-per-sample 代码可能会导致缓冲区溢出。访问冲突异常和丢失对象——你可能在正确的轨道上 GC 过早地吃掉你的数据——看起来像是对不安全代码的半生不熟的尝试。这是你可以在不安全的代码中做的事情吗?从头开始,正确的编组?
-
你试过
SoundPlayer类吗? msdn.microsoft.com/en-us/library/system.media.soundplayer.aspx -
@ssamuel 我当时正在输出 8 位样本,其中 WaveOut 配置为 8 位。但是它似乎不适用于 16 位模式...
-
@ssamuel 问题是我什至无法开始烤任何东西,更不用说从头开始了;)也许我应该放弃并买一只宠物...... :(