帮助从麦克风捕获声音并在C#中播放?

时间:2010-03-03 18:41:26

标签: c# directx

嗨,我有这个代码,我有2个错误,我无法摆脱。

有任何帮助吗?

namespace pleasework
{
    public partial class Form1 : Form
    {
        private Thread _echoThread;
        private Capture _captureDevice;
        private CaptureBuffer _captureBuffer;
        private Device _playbackDevice;
        private SecondaryBuffer _playbackBuffer;
        private int _bufferSize;
        private const int _bufferPositions = 4;
        private AutoResetEvent _notificationEvent = null;
        private BufferPositionNotify[] _positionNotify = new BufferPositionNotify[_bufferPositions + 1];
        private Notify _echoNotify = null;

        private void EchoThread()
        {
            int offset = 0;



            _captureBuffer.Start(true);
            _playbackBuffer.Play(0, BufferPlayFlags.Looping);
            //byte[] buffer = (byte[])_captureBuffer.Read(offset, typeof(byte), LockFlag.FromWriteCursor, _bufferSize);


            for (; ; )
            {
                _notificationEvent.WaitOne(Timeout.Infinite, true);

                byte[] buffer = (byte[])_captureBuffer.Read(offset, typeof(byte), LockFlag.None, _bufferSize);

                _playbackBuffer.Write(offset, buffer, LockFlag.None);
                offset = (offset + _bufferSize) % (_bufferPositions * _bufferSize);
            }

        }

        public Form1()
        {
            CheckForIllegalCrossThreadCalls = false;
            InitializeComponent();

            _captureDevice = new Capture();

            short channels = 2;


            short bitsPerSample = 16;


            int samplesPerSecond = 22050;

            //Set up the wave format to be captured
            WaveFormat waveFormat = new WaveFormat();
            waveFormat.Channels = channels;
            waveFormat.FormatTag = WaveFormatTag.Pcm;
            waveFormat.SamplesPerSecond = samplesPerSecond;
            waveFormat.BitsPerSample = bitsPerSample;
            waveFormat.BlockAlign = (short)(channels * (bitsPerSample / 8));
            waveFormat.AverageBytesPerSecond = waveFormat.BlockAlign * samplesPerSecond;

            _bufferSize = waveFormat.AverageBytesPerSecond / 20;

            CaptureBufferDescription captureBufferDescription = new CaptureBufferDescription();
            captureBufferDescription.BufferBytes = _bufferPositions * _bufferSize;
            captureBufferDescription.Format = waveFormat;
            _captureBuffer = new CaptureBuffer(captureBufferDescription, _captureDevice);

            _playbackDevice = new Device();
            _playbackDevice.SetCooperativeLevel(this, CooperativeLevel.Normal);

            BufferDescription playbackBufferDescription = new BufferDescription();
            playbackBufferDescription.BufferBytes = _bufferPositions * _bufferSize;
            playbackBufferDescription.Format = waveFormat;
            _playbackBuffer = new SecondaryBuffer(playbackBufferDescription, _playbackDevice);

            _echoThread = new Thread(new ThreadStart(EchoThread));
            _echoThread.Start();


            _notificationEvent = new AutoResetEvent(false);
            for (int i = 0; i < _bufferPositions; i++)
            {

                _positionNotify.Offset = (_bufferSize * i) + _bufferSize - 1; // got error here
                _positionNotify.EventNotifyHandle = _notificationEvent.SafeWaitHandle.DangerousGetHandle();// got error here
            }
            _echoNotify = new Notify(_captureBuffer);
            _echoNotify.SetNotificationPositions(_positionNotify, _bufferPositions);

        }

        private void EchoClose(object sender, FormClosingEventArgs e)
        {
            _echoThread.Abort();
        }
    }
}

谢谢!

2 个答案:

答案 0 :(得分:1)

您正在将_positionNotify设置为包含_bufferPosition + 1元素的数组。但是,当您处于for循环中时,您永远不会指定要为其设置Offset和EventNotifyHandle的元素。此外,我认为您需要添加一行,以便实际创建BufferPositionNotify结构的新实例。尝试将这些行更改为以下内容:

        for (int i = 0; i < _bufferPositions; i++)
        {
            _positionNotify[i] = new BufferPositionNotify();
            _positionNotify[i].Offset = (_bufferSize * i) + _bufferSize - 1;
            _positionNotify[i].EventNotifyHandle = 
                _notificationEvent.SafeWaitHandle.DangerousGetHandle();
        }

答案 1 :(得分:0)

我试过了代码。首先,它没有用。 而不是:private BufferPositionNotify[] _positionNotify = new BufferPositionNotify[_bufferPositions + 1];它应该是private BufferPositionNotify[] _positionNotify = new BufferPositionNotify[_bufferPositions];。另外,你的数组中有一个元素。