我希望将音频静音一段时间,让我们说它从2秒开始直到4秒的播放持续时间,即2秒钟。
我想为50个不同的Audios执行此操作,其中Muting具有不同的开始和停止时间。目前,我正在使用两个System.Timer
类的对象,其间隔为第一个为开始时间,第二个为停止时间为Muting,我有50个if
子句来检查50个音频和设置他们的启动和停止计时器就像这样:
//50 checks
AudioFileReader ar;
Timer start_timer = new Timer(),stop_timer=new Timer();
public Form1()
{
InitializeComponent();
ar = new AudioFileReader(@"D:\SampleDegradedSpeech.wav");
var a = new WaveOut();
a.Init(ar);
a.Play();
start_timer.Interval = //start time;
stop_timer.Interval = //stop time;
start_timer.Tick += t1_Tick;
start_timer.Start();
stop_timer.Tick+=t2_Tick;
stop_timer.Start();
}
private void t2_Tick(object sender, EventArgs e)
{
ar.Volume = 1;
stop_timer.Stop();
}
private void t1_Tick(object sender, EventArgs e)
{
ar.Volume = 0;
start_timer.Stop();
}
还有其他/更好的方法吗?
两个计时器的任何替换?
像ar.mute(start,stop)
?
答案 0 :(得分:0)
当底层流到达该时间点时,您可以编写自己的IWaveProvider
实现,它包裹您的WaveSource
以将Read
方法中的样本字节设置为0。到达静音期结束时,您将停止更改字节数组。
这是MutingReader
的简单实现:
private class MutingReader : IWaveProvider
{
private TimeSpan _start;
private TimeSpan _end;
private WaveStream _stream;
// constructor
public MutingReader(WaveStream stream, TimeSpan start, TimeSpan end)
{
_stream = stream;
_start = start;
_end = end;
}
// gets called each time the WaveOut needs more bytes
public int Read(byte[] array, int offset, int count)
{
Debug.WriteLine(_stream.CurrentTime);
var samples = _stream.Read(array, offset, count);
// if we are between our Start and End Time stamps
if (_stream.CurrentTime > _start &&
_stream.CurrentTime < _end)
{
// silence by only returning zeroes in the array
for (int i = 0; i < count; i++)
{
array[i + offset] = 0;
}
}
return samples;
}
#region IWaveProvider Members
public WaveFormat WaveFormat
{
get { return _stream.WaveFormat; }
}
#endregion
}
您可以按如下方式使用上述实现:
var wo = new NAudio.Wave.WaveOutEvent();
var reader = new MutingReader(
new WaveFileReader( @"v1.wav"),
new TimeSpan(0,0,2), // mute after 2 seconds
new TimeSpan(0,0,4)); // unmute after 4 seconds
wo.Init(reader);
wo.Play();