Esempio n. 1
0
        public double[] SynthetizeNoise(Bitmap image, int samplerate)
        {
            using (new DebugTimer("Spectrogram: SynthetizeNoise()"))
            {
                int samples = (int)image.Width * samplerate / pixpersec;

                Complex[] noise = SpectrogramUtils.GetPinkNoise(samplerate * 10);                 // 10 sec loop

                double     filterscale = ((double)noise.Length * 2) / samplerate;
                Filterbank filterbank  = Filterbank.GetFilterbank(frequency_axis, filterscale, basefreq, bandwidth, overlap);

                int top_index = (int)(maxfreq * filterscale);

                var @out = new double[samples];

                for (int bandidx = 0; bandidx < image.Height; ++bandidx)
                {
                    //if (cancelled())
                    //	return List<int>();
                    OutputBandProgress(bandidx, image.Height - 1);

                    // filter noise
                    Pair <int, int> range = filterbank.GetBand(bandidx);
                    //std::cout << bandidx << "/"<<image.height()<<"\n";
                    Console.Out.WriteLine("(noise) sample: {0}", range.Second - range.First);

                    var filtered_noise = new Complex[noise.Length];
                    // TODO: copy noise into filtered_noise array
                    //std.copy(noise.begin()+range.first, noise.begin()+Math.Min(range.second, top_index), filtered_noise.begin()+range.first);

                    //apply_window(filtered_noise, range.first, filterscale);

                    // ifft noise
                    double[] noise_mod = SpectrogramUtils.padded_IFFT(ref filtered_noise);

                    // resample spectrogram band
                    double[] envelope = SpectrogramUtils.Resample(EnvelopeFromSpectrogram(image, bandidx), samples);

                    // modulate with looped noise
                    for (uint i = 0; i < samples; ++i)
                    {
                        @out[i] += envelope[i] * noise_mod[i % noise_mod.Length];
                    }
                }

                SpectrogramUtils.NormalizeSignal(ref @out);
                return(@out);
            }
        }
Esempio n. 2
0
        public double[] SynthetizeSine(Bitmap image, int samplerate)
        {
            using (new DebugTimer("Spectrogram: SynthetizeSine(Bitmap)"))
            {
                int samples  = image.Width * samplerate / pixpersec;
                var spectrum = new Complex[samples / 2 + 1];

                double filterscale = ((double)spectrum.Length * 2) / samplerate;

                Filterbank filterbank = Filterbank.GetFilterbank(frequency_axis, filterscale, basefreq, bandwidth, overlap);

                for (int bandidx = 0; bandidx < image.Height; ++bandidx)
                {
                    // TODO: support cancelling this process

                    OutputBandProgress(bandidx, image.Height);

                    double[] envelope = EnvelopeFromSpectrogram(image, bandidx);
                    // Find maximum number when all numbers are made positive.
                    //double max = envelope.Max((b) => Math.Abs(b));
                    //Console.WriteLine(max);

                    // random phase between +-pi
                    double phase = SpectrogramUtils.RandomDoubleMinus1ToPlus1() * Math.PI;

                    var bandsignal = new double[envelope.Length * 2];
                    for (int j = 0; j < 4; ++j)
                    {
                        double sine = Math.Cos(j * Math.PI / 2 + phase);
                        for (int i = j; i < bandsignal.Length; i += 4)
                        {
                            bandsignal[i] = envelope[i / 2] * sine;
                        }
                    }

                    var filterband = SpectrogramUtils.padded_FFT(ref bandsignal);

                    for (int i = 0; i < filterband.Length; ++i)
                    {
                        double x = (double)i / filterband.Length;

                        // normalized blackman window antiderivative
                        filterband[i] *= x - ((0.5 / (2.0 * Math.PI)) * Math.Sin(2.0 * Math.PI * x) + (0.08 / (4.0 * Math.PI)) * Math.Sin(4.0 * Math.PI * x) / 0.42);
                    }

                    //Console.Out.WriteLine("Spectrum size: {0}", spectrum.Length);
                    //std::cout << bandidx << ". filterband size: " << filterband.Length << "; start: " << filterbank->GetBand(bandidx).first <<"; end: " << filterbank->GetBand(bandidx).second << "\n";

                    double center = filterbank.GetCenter(bandidx);
                    double offset = Math.Max((double)0, center - filterband.Length / 2);

                    //Console.Out.WriteLine("Offset: {0} = {1} hz", offset, offset/filterscale);

                    for (int i = 0; i < filterband.Length; ++i)
                    {
                        int spectrumIndex = (int)(offset + i);
                        if (spectrumIndex > 0 && spectrumIndex < spectrum.Length)
                        {
                            spectrum[spectrumIndex] += filterband[i];
                        }
                    }
                }

                double[] @out = SpectrogramUtils.padded_IFFT(ref spectrum);

                Console.Out.WriteLine("Samples: {0} -> {1}", @out.Length, samples);

                SpectrogramUtils.NormalizeSignal(ref @out);
                return(@out);
            }
        }