/// <summary> /// Amplitude envelope builder /// Save maximum values /// </summary> public Samples Build(Samples source, int newBitrate = 20, bool differentiate = false) { float koeff = 1f * newBitrate /source.Bitrate; var values = source.Values; var resValues = new float[(int)(values.Length * koeff)+1]; for (var i = values.Length - 2; i >= 0; i--) { var newIndex = (int) (i*koeff); var prevValue = resValues[newIndex]; var value = values[i]; if (differentiate) { value = values[i + 1] - value; } value = Math.Abs(value); if (prevValue < value) { resValues[newIndex] = value; } } return new Samples() { Bitrate = newBitrate, Values = resValues }; }
public void DrawOneSide(Samples samples, Graphics gr, Rectangle bounds, bool normalize = false) { var kx = bounds.Width / samples.Values.Length; var ky = bounds.Height; var cy = bounds.Bottom; var cx = bounds.Left; var values = samples.Values; if (normalize) { var s = samples.Clone(); s.Normalize(); values = s.Values; } using (var pen = new Pen(ForeColor)) for (int i = 0; i < values.Length; i++) { var x = i * kx; var y = values[i]; if (y > 1) y = 1; if (y < -1) continue; y = y * ky; gr.DrawLine(pen, cx + x, cy, cx + x, cy - y); } }
public Samples Clone() { var result = new Samples(); result.Bitrate = Bitrate; result.Values = new float[Values.Length]; Array.Copy(Values, result.Values, Values.Length); return result; }
public void Process(Audio item, AudioInfo info) { var tempogram = new Tempogram(); //get maximum values Samples samples = new EnvelopeProcessor(factory).Build(info.Samples, 32, false); var newSamples = new Samples() { Values = new float[samples.Values.Length], Bitrate = samples.Bitrate }; var intensity = 0; for (int i = 0; i < samples.Values.Length - 1; i++) { var diff = samples.Values[i + 1] - samples.Values[i]; samples.Values[i] = diff > 0 ? diff : 0; //разница между всеми амплитудами newSamples.Values[i] = diff; if (diff > minAmplitudeChangeForIntensityRate) { intensity++; } } samples.Values[samples.Values.Length - 1] = 0; newSamples.Values[samples.Values.Length - 1] = 0; var durationOfTrack = samples.Values.Length / samples.Bitrate;//time of sound var maxShift = (int)(samples.Values.Length * (maxRithmDuration / durationOfTrack)); var autoCorr1 = AutoCorr(samples.Values, maxShift, 5); var autoCorr2 = AutoCorr(newSamples.Values, maxShift, 2); var lengthCorr1 = (float)autoCorr1.Length; var log2 = Math.Log(2); var list1 = new List<KeyValuePair<float, float>>(); var list2 = new List<KeyValuePair<float, float>>(); for (int i = 0; i < lengthCorr1; i++) { var j = i / (float)lengthCorr1; j = (float)(Math.Log(j + 1) / log2); list1.Add(new KeyValuePair<float, float>(j, autoCorr1[i])); var v = autoCorr2[i]; list2.Add(new KeyValuePair<float, float>(j, v > 0 ? v : 0)); } tempogram.LongTempogram.Build(list1); tempogram.ShortTempogram.Build(list2); tempogram.Intensity = (float)intensity / durationOfTrack; CalcTempo(tempogram); //save to audio item item.Data.Add(tempogram); }
public Envelope(Samples samples) { var values = samples.Values; //pack packedValues = new byte[values.Length / 2]; for (int i = 0; i < values.Length; i += 2) { var v1 = (int)(16 * values[i]); var v2 = (int)(16 * values[i + 1]); if (v1 > 15) v1 = 15; if (v2 > 15) v2 = 15; packedValues[i / 2] = (byte)((v1 << 4) + v2); } }