Example #1
0
        /// <summary>
        /// Processes data and frees buffers that have been used by the application.
        /// </summary>
        private void ProcessDone()
        {
            IntPtr header;

            // Pull the header data back out of unmanaged memory
            lock (this.bufferingLock)
            {
                header = this.bufferReleaseQueue.Dequeue();
                Monitor.Pulse(this.bufferingLock);
            }

            NativeMethods.WAVEHDR pwh = (NativeMethods.WAVEHDR)Marshal.PtrToStructure(header, typeof(NativeMethods.WAVEHDR));

            // Find and copy the buffer data
            IntPtr data = pwh.lpData;

            // Copy the data and fire the DataReady event if necessary
            if (pwh.dwBytesRecorded > 0 && this.DataReady != null)
            {
                byte[] newData = new byte[pwh.dwBytesRecorded];
                Marshal.Copy(data, newData, 0, (int)pwh.dwBytesRecorded);
                this.DataReady(this, new DataReadyEventArgs(newData));
            }

            // Unprepare the header
            NativeMethods.Throw(
                NativeMethods.waveInUnprepareHeader(this.handle, header, (uint)Marshal.SizeOf(typeof(NativeMethods.WAVEHDR))),
                NativeMethods.ErrorSource.WaveIn);

            // Free the unmanaged memory
            Marshal.FreeHGlobal(data);
            Marshal.FreeHGlobal(header);
        }
Example #2
0
        /// <summary>
        /// Writes a block of data (in the current forma, set during Open) to the device.
        /// </summary>
        /// <param name="bufferData">The data to send to the device.</param>
        public void Write(byte[] bufferData)
        {
            lock (this.startStopLock)
            {
                IntPtr mem = Marshal.AllocHGlobal(bufferData.Length);
                Marshal.Copy(bufferData, 0, mem, bufferData.Length);

                NativeMethods.WAVEHDR pwh = new NativeMethods.WAVEHDR();
                pwh.dwBufferLength = (uint)bufferData.Length;
                pwh.dwFlags        = 0;
                pwh.lpData         = mem;
                pwh.dwUser         = new IntPtr(12345);

                IntPtr header = Marshal.AllocHGlobal(Marshal.SizeOf(pwh));
                Marshal.StructureToPtr(pwh, header, false);

                NativeMethods.Throw(
                    NativeMethods.waveOutPrepareHeader(this.handle, header, (uint)Marshal.SizeOf(typeof(NativeMethods.WAVEHDR))),
                    NativeMethods.ErrorSource.WaveOut);

                NativeMethods.Throw(
                    NativeMethods.waveOutWrite(this.handle, header, (uint)Marshal.SizeOf(typeof(NativeMethods.WAVEHDR))),
                    NativeMethods.ErrorSource.WaveOut);

                lock (this.bufferingLock)
                {
                    this.bufferQueueCount++;
                    Monitor.Pulse(this.bufferingLock);
                }
            }
        }
Example #3
0
        /// <summary>
        /// Adds a buffer to the queue.
        /// </summary>
        private void AddBuffer()
        {
            // Allocate unmanaged memory for the buffer
            int    bufferLength = this.bufferSize * this.recordingFormat.BlockAlign;
            IntPtr mem          = Marshal.AllocHGlobal(bufferLength);

            // Initialize the buffer header, including a reference to the buffer memory
            NativeMethods.WAVEHDR pwh = new NativeMethods.WAVEHDR();
            pwh.dwBufferLength = (uint)bufferLength;
            pwh.dwFlags        = 0;
            pwh.lpData         = mem;
            pwh.dwUser         = new IntPtr(12345);

            // Copy the header into unmanaged memory
            IntPtr header = Marshal.AllocHGlobal(Marshal.SizeOf(pwh));

            Marshal.StructureToPtr(pwh, header, false);

            // Prepare the header
            NativeMethods.Throw(
                NativeMethods.waveInPrepareHeader(this.handle, header, (uint)Marshal.SizeOf(typeof(NativeMethods.WAVEHDR))),
                NativeMethods.ErrorSource.WaveOut);

            // Add the buffer to the device
            NativeMethods.Throw(
                NativeMethods.waveInAddBuffer(this.handle, header, (uint)Marshal.SizeOf(typeof(NativeMethods.WAVEHDR))),
                NativeMethods.ErrorSource.WaveOut);

            lock (this.bufferingLock)
            {
                this.bufferQueueCount++;
                Monitor.Pulse(this.bufferingLock);
            }
        }
Example #4
0
        /// <summary>
        /// Frees buffers that have been used by the application.
        /// </summary>
        private void ProcessDone()
        {
            IntPtr header;

            // Pull the header data back out of unmanaged memory
            lock (this.bufferingLock)
            {
                header = this.bufferReleaseQueue.Dequeue();
                Monitor.Pulse(this.bufferingLock);
            }

            NativeMethods.WAVEHDR pwh = (NativeMethods.WAVEHDR)Marshal.PtrToStructure(header, typeof(NativeMethods.WAVEHDR));
            IntPtr data = pwh.lpData;

            NativeMethods.Throw(
                NativeMethods.waveOutUnprepareHeader(this.handle, header, (uint)Marshal.SizeOf(typeof(NativeMethods.WAVEHDR))),
                NativeMethods.ErrorSource.WaveOut);

            Marshal.FreeHGlobal(data);
            Marshal.FreeHGlobal(header);
        }
Example #5
0
        public static void Play(double[] signal, int samplingRate)
        {
            // Dies ist noch sehr unsauber!
            // TODO: auf Fehler reagieren; Speicherlecks vermeiden
            // TODO: Iterator statt komplettem Array benutzen

            short[] buffer = new short[signal.Length];
            for (int i = 0; i < signal.Length; i++)
            {
                buffer[i] = (short)(short.MaxValue * signal[i]);
            }
            GCHandle hBuffer = GCHandle.Alloc(buffer, GCHandleType.Pinned);

            IntPtr hWaveOut = IntPtr.Zero;

            NativeMethods.WAVEFORMATEX format = new NativeMethods.WAVEFORMATEX();
            format.wFormatTag      = 1;
            format.nChannels       = 1;
            format.nSamplesPerSec  = (uint)samplingRate;
            format.nAvgBytesPerSec = (uint)(samplingRate * sizeof(short));
            format.nBlockAlign     = sizeof(short);
            format.wBitsPerSample  = 16;
            format.cbSize          = 0;
            NativeMethods.waveOutOpen(ref hWaveOut, new IntPtr(-1), ref format, IntPtr.Zero, IntPtr.Zero, 0);
            NativeMethods.WAVEHDR header = new NativeMethods.WAVEHDR();
            header.lpData         = Marshal.UnsafeAddrOfPinnedArrayElement(buffer, 0);
            header.dwBufferLength = (uint)(buffer.Length * sizeof(short));
            NativeMethods.waveOutPrepareHeader(hWaveOut, ref header, (uint)Marshal.SizeOf(header));
            NativeMethods.waveOutWrite(hWaveOut, ref header, (uint)Marshal.SizeOf(header));
            while ((header.dwFlags & 1) == 0)
            {
                System.Threading.Thread.Sleep(100);
            }
            NativeMethods.waveOutUnprepareHeader(hWaveOut, ref header, (uint)Marshal.SizeOf(header));
            NativeMethods.waveOutClose(hWaveOut);

            hBuffer.Free();
        }