public void GetMidiCodes(int offset, int fftSize = 4096, int maxFreq = 5000) { AudioClip clip; float[] real, im, window; FloatFFT fft; string assetPath; float binWidth; List <FFTBinInfo> binInfos; int i; real = new float[fftSize]; im = new float[fftSize]; window = new float[fftSize]; GATMaths.MakeHammingWindow(window); fft = new FloatFFT(); fft.init(( uint )Mathf.Log(fftSize, 2)); binWidth = ( float )_sampleRate / fftSize; int maxBin = ( int )(( float )maxFreq / binWidth); foreach (GATSampleInfo info in _sampleInfos) { assetPath = AssetDatabase.GUIDToAssetPath(info.GUID); clip = AssetDatabase.LoadAssetAtPath(assetPath, typeof(AudioClip)) as AudioClip; if (clip.channels > 1) { throw new GATException("Get Midi Codes is a beta feature only available for mono clips"); } clip.GetData(real, offset); System.Array.Clear(im, 0, im.Length); fft.run(real, im); for (i = 0; i < maxBin; i++) { real[i] = Mathf.Sqrt(real[i] * real[i] + im[i] * im[i]); } binInfos = FFTBinInfo.GetLowerMaxBins(real, 0, maxBin, binWidth, .2f); info.MidiCode = binInfos[binInfos.Count - 1].GetMidiCode(); } SortByMidiCode(); }
public static List <FFTBinInfo> GetLowerMaxBins(float[] magnitudes, int fromIndex, int toIndex, float binFrequencyWidth, float magThresholdRatio) { List <FFTBinInfo> maxBins = new List <FFTBinInfo>(); FFTBinInfo binInfo; int maxIndex; float magThreshold; fromIndex++; toIndex--; maxIndex = GATMaths.GetIndexOfMaxValue(magnitudes, fromIndex, toIndex); binInfo = new FFTBinInfo(magnitudes, maxIndex, binFrequencyWidth); maxBins.Add(binInfo); magThreshold = binInfo.InterpolatedMagnitude * magThresholdRatio; while (true) { toIndex = binInfo.BinIndex - 1; if (toIndex - fromIndex < 3) { break; } maxIndex = GATMaths.GetIndexOfMaxValue(magnitudes, fromIndex, toIndex); binInfo = new FFTBinInfo(magnitudes, maxIndex, binFrequencyWidth); if (binInfo.InterpolatedMagnitude < magThreshold) { break; } maxBins.Add(binInfo); } return(maxBins); }
public static List<FFTBinInfo> GetLowerMaxBins( float[] magnitudes, int fromIndex, int toIndex, float binFrequencyWidth, float magThresholdRatio ) { List< FFTBinInfo > maxBins = new List< FFTBinInfo >(); FFTBinInfo binInfo; int maxIndex; float magThreshold; fromIndex ++; toIndex --; maxIndex = GATMaths.GetIndexOfMaxValue( magnitudes, fromIndex, toIndex ); binInfo = new FFTBinInfo( magnitudes, maxIndex, binFrequencyWidth ); maxBins.Add( binInfo ); magThreshold = binInfo.InterpolatedMagnitude * magThresholdRatio; while( true ) { toIndex = binInfo.BinIndex - 1; if( toIndex - fromIndex < 3 ) break; maxIndex = GATMaths.GetIndexOfMaxValue( magnitudes, fromIndex, toIndex ); binInfo = new FFTBinInfo( magnitudes, maxIndex, binFrequencyWidth ); if( binInfo.InterpolatedMagnitude < magThreshold ) break; maxBins.Add( binInfo ); } return maxBins; }