TunerDlg.cs

using System;

using System.Windows.Forms;

 

using Microsoft.DirectX.DirectSound;

 

namespace DZouch

{

    public partial class TunerDlg : Form

    {

        public static int BUFFER_SIZE = 32768;

 

        public class DeviceInfo

        {

            protected DeviceInformation info;

 

            public DeviceInfo(DeviceInformation di)

            {

                info = di;

            }

 

            public Guid DriverGuid { get { return info.DriverGuid; } }

 

            public override string ToString()

            {

                return info.Description;

            }

        }

 

        public class Buffer

        {

            private double[] buffer;

 

            public Buffer(int size)

            {

                buffer = new double[size];

            }

 

            public double[] Data() { return buffer; }

 

            public void PushData(double[] data)

            {

                if (data == null || buffer == null)

                    return;

 

                if (data.Length < buffer.Length)

                {

                    Array.Copy(buffer, data.Length, buffer, 0, buffer.Length - data.Length);

                    Array.Copy(data, 0, buffer, buffer.Length - data.Length, data.Length);

                }

                else

                {

                    Array.Copy(data, data.Length - buffer.Length, buffer, 0, buffer.Length);

                }

            }

        }

 

 

        private Timer timer = new Timer();

        private SoundCapture capture;

        private Buffer leftBuffer = new Buffer(BUFFER_SIZE);

        private Buffer rightBuffer = new Buffer(BUFFER_SIZE);

 

        public TunerDlg()

        {

            InitializeComponent();

 

            timer.Tick += new EventHandler(timer_Tick);

        }

 

        protected override void OnLoad(EventArgs e)

        {

            base.OnLoad(e);

 

            CaptureDevicesCollection devices = new CaptureDevicesCollection();

            foreach (DeviceInformation info in devices)

            {

                int line = comboInput.Items.Add(new DeviceInfo(info));

                if (info.DriverGuid == Properties.Settings.Default.Device)

                    comboInput.SelectedIndex = line;

            }

        }

 

        protected override void OnClosed(EventArgs e)

        {

            base.OnClosed(e);

 

            StopCapture();

 

            Properties.Settings.Default.Save();

        }

 

        private void timer_Tick(object sender, EventArgs e)

        {

            short[] data = capture.Pull();

            short[] leftData = LeftChannel(data);

            short[] rightData = RightChannel(data);

            var sampleRate = SoundCapture.Frequency();

 

            leftIndicator.Update(leftData);

            rightIndicator.Update(rightData);

 

            leftBuffer.PushData(ToDouble(leftData));

            rightBuffer.PushData(ToDouble(rightData));

            FFT.RealFourier leftFFT = FFT.HannWindow.GetSpectrum(leftBuffer.Data());

            FFT.RealFourier rightFFT = FFT.HannWindow.GetSpectrum(rightBuffer.Data());

            displayLeft.SetFFT(leftFFT);

            displayLeft.SetFreq(leftFFT.PeakFreq(sampleRate), sampleRate);

            displayRight.SetFFT(rightFFT);

            displayRight.SetFreq(rightFFT.PeakFreq(sampleRate), sampleRate);

        }

 

        private static double[] ToDouble(short[] data)

        {

            if (data == null)

                return null;

 

            double[] output = new double[data.Length];

            for (int index = 0; index < data.Length; index++)

            {

                output[index] = data[index];

            }

 

            return output;

        }

 

        private static short[] LeftChannel(short[] data)

        {

            if (data == null)

                return null;

 

            short[] left = new short[data.Length / 2];

            int index = 0;

            foreach (short sample in data)

            {

                if (index % 2 == 0)

                    left[index / 2] = sample;

                index++;

            }

 

            return left;

        }

 

        private static short[] RightChannel(short[] data)

        {

            if (data == null)

                return null;

 

            short[] right = new short[data.Length / 2];

            int index = 0;

            foreach (short sample in data)

            {

                if (index % 2 != 0)

                    right[index / 2] = sample;

                index++;

            }

 

            return right;

        }

 

        private void comboInput_SelectedIndexChanged(object sender, EventArgs e)

        {

            StopCapture();

            DeviceInfo info = comboInput.SelectedItem as DeviceInfo;

            if (info != null)

            {

                StartCapture(info.DriverGuid);

                Properties.Settings.Default.Device = info.DriverGuid;

            }

        }

 

        private void buttonClose_Click(object sender, EventArgs e)

        {

            Close();

        }

 

        private void StartCapture(Guid guid)

        {

            leftIndicator.Reset();

            rightIndicator.Reset();

            capture = new SoundCapture(guid);

            if (capture != null)

            {

                capture.Start();

                timer.Interval = 100;

                timer.Start();

            }

        }

 

        private void StopCapture()

        {

            if (capture != null)

            {

                capture.Stop();

                timer.Stop();

                capture.Dispose();

                capture = null;

            }

 

            leftIndicator.Reset();

            rightIndicator.Reset();

        }

    }

}