On Sat, Jan 16, 2016 at 09:09:21PM +0100, Paul B Mahol wrote: > Signed-off-by: Paul B Mahol <one...@gmail.com> [...] > +static int filter_frame(AVFilterLink *inlink, AVFrame *frame) > +{ > + AVFilterContext *ctx = inlink->dst; > + AVFilterLink *outlink = ctx->outputs[0]; > + AFFTFiltContext *s = ctx->priv; > + const int window_size = s->window_size; > + const float f = 1. / window_size; > + double values[VAR_VARS_NB]; > + AVFrame *out, *in = NULL; > + int ch, n, ret, i, j, k; > + int start = s->start, end = s->end; > + > + av_audio_fifo_write(s->fifo, (void **)frame->extended_data, > frame->nb_samples); > + av_frame_free(&frame); > + > + while (av_audio_fifo_size(s->fifo) >= window_size) { > + in = ff_get_audio_buffer(outlink, window_size); > + if (!in) > + return AVERROR(ENOMEM); > + > + ret = av_audio_fifo_peek(s->fifo, (void **)in->extended_data, > window_size); > + if (ret < 0) > + break; > + > + for (ch = 0; ch < inlink->channels; ch++) { > + const float *src = (float *)in->extended_data[ch]; > + FFTComplex *fft_data = s->fft_data[ch]; > + > + for (n = 0; n < in->nb_samples; n++) { > + fft_data[n].re = src[n] * s->window_func_lut[n]; > + fft_data[n].im = 0; > + } > + > + for (; n < window_size; n++) { > + fft_data[n].re = 0; > + fft_data[n].im = 0; > + } > + } > + > + values[VAR_PTS] = s->pts; > + values[VAR_SAMPLE_RATE] = inlink->sample_rate; > + values[VAR_CHANNELS] = inlink->channels; > + > + for (ch = 0; ch < inlink->channels; ch++) { > + FFTComplex *fft_data = s->fft_data[ch]; > + float *buf = (float *)s->buffer->extended_data[ch]; > + int x; > + > + values[VAR_CHANNEL] = ch; > + > + av_fft_permute(s->fft, fft_data); > + av_fft_calc(s->fft, fft_data); > + > + for (n = 0; n < window_size / 2; n++) { > + float ff; > + > + values[VAR_BIN] = n; > + > + ff = av_expr_eval(s->expr[ch], values, s); > + fft_data[n].re *= ff; > + fft_data[n].im *= ff;
if you use a complex valued FFT then allowing complex values from the user somehow could make sense maybe a real / imag expr > + } > + > + for (n = window_size / 2 + 1, x = window_size / 2 - 1; n < > window_size; n++, x--) { > + fft_data[n].re = fft_data[x].re; > + fft_data[n].im = -fft_data[x].im; > + } > + > + av_fft_permute(s->ifft, fft_data); > + av_fft_calc(s->ifft, fft_data); > + > + start = s->start; > + end = s->end; > + k = end; > + for (i = 0, j = start; j < k && i < window_size; i++, j++) { > + buf[j] += s->fft_data[ch][i].re * f; > + } > + > + for (; i < window_size; i++, j++) { > + buf[j] = s->fft_data[ch][i].re * f; > + } rescaling by a constant can likely be merged into something (window or expr based coeffs) [...] -- Michael GnuPG fingerprint: 9FF2128B147EF6730BADF133611EC787040B0FAB The bravest are surely those who have the clearest vision of what is before them, glory and danger alike, and yet notwithstanding go out to meet it. -- Thucydides
signature.asc
Description: Digital signature
_______________________________________________ ffmpeg-devel mailing list ffmpeg-devel@ffmpeg.org http://ffmpeg.org/mailman/listinfo/ffmpeg-devel