Skip to content

Instantly share code, notes, and snippets.

@DevJohnC
Created April 26, 2013 23:45
Show Gist options
  • Select an option

  • Save DevJohnC/5471179 to your computer and use it in GitHub Desktop.

Select an option

Save DevJohnC/5471179 to your computer and use it in GitHub Desktop.
WPF Testing FFT
using System;
using System.IO;
using System.Windows;
using FragLabs.Audio.Engines;
using FragLabs.Audio.Engines.OpenAL;
namespace VoiceRecognition
{
/// <summary>
/// Interaction logic for MainWindow.xaml
/// </summary>
public partial class MainWindow : Window
{
public static event EventHandler<FFTEventArgs> FftRan;
protected virtual void OnFftRan(FFTEventArgs e)
{
var handler = FftRan;
if (handler != null) handler(this, e);
}
public static Stream InputStream = null;
public static CaptureDevice InputDevice = null;
public static int SampleRate = 48000;
public static int BitDepth = 16;
public static int Channels = 1;
public static byte[] ReadBuffer;
public static int SampleSizeMs = 100;
public static LiveAudioInfo LiveAudioInfo = null;
public static FFT Fft = new FFT();
public MainWindow()
{
InitializeComponent();
Loaded += OnLoaded;
Unloaded += OnUnloaded;
}
private void OnUnloaded(object sender, RoutedEventArgs routedEventArgs)
{
InputStream.Close();
InputStream.Dispose();
InputStream = null;
LiveAudioInfo.Close();
LiveAudioInfo = null;
}
private void OnLoaded(object sender, RoutedEventArgs routedEventArgs)
{
var bufferSize = ((SampleRate/1000)*((BitDepth/8)*Channels))*SampleSizeMs;
ReadBuffer = new byte[bufferSize];
var sampleCount = (uint) (bufferSize/((BitDepth/8)*Channels));
Fft.init(LogN(sampleCount));
InputDevice = OpenALHelper.CaptureDevices[0];
InputStream = InputDevice.OpenStream(SampleRate, OpenALAudioFormat.Mono16Bit, SampleSizeMs); // read 10ms of audio data each "read" operation
InputStream.BeginRead(ReadBuffer, 0, ReadBuffer.Length, OnReadComplete, null);
LiveAudioInfo = new LiveAudioInfo();
LiveAudioInfo.Show();
}
private void OnReadComplete(IAsyncResult ar)
{
if (InputStream == null)
return;
var readBytes = InputStream.EndRead(ar);
var samples = Convert16BitToDouble(ReadBuffer);
var real = new double[samples.Length];
var imaginary = new double[samples.Length];
Buffer.BlockCopy(samples, 0, real, 0, samples.Length);
Fft.run(real, imaginary);
OnFftRan(new FFTEventArgs() {Fft = Fft});
InputStream.BeginRead(ReadBuffer, 0, ReadBuffer.Length, OnReadComplete, null);
}
private uint LogN(uint input)
{
return (uint) (Math.Log(input)/Math.Log(2));
}
public double[] Convert16BitToDouble(byte[] input)
{
var inputSamples = input.Length / (BitDepth / 8);
var output = new double[inputSamples];
var outputIndex = 0;
for (var n = 0; n < inputSamples; n++)
{
short sample = BitConverter.ToInt16(input, n * 2);
output[outputIndex++] = sample / 32768f;
}
return output;
}
}
public class FFTEventArgs : EventArgs
{
public FFT Fft { get; set; }
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment