FFmpeg
window_func.h
Go to the documentation of this file.
1 /*
2  * Copyright (c) 2015 Paul B Mahol
3  *
4  * This file is part of FFmpeg.
5  *
6  * FFmpeg is free software; you can redistribute it and/or
7  * modify it under the terms of the GNU Lesser General Public
8  * License as published by the Free Software Foundation; either
9  * version 2.1 of the License, or (at your option) any later version.
10  *
11  * FFmpeg is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14  * Lesser General Public License for more details.
15  *
16  * You should have received a copy of the GNU Lesser General Public
17  * License along with FFmpeg; if not, write to the Free Software
18  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
19  */
20 
21 
22 #ifndef AVFILTER_WINDOW_FUNC_H
23 #define AVFILTER_WINDOW_FUNC_H
24 
25 #include <math.h>
26 #include "libavutil/avassert.h"
27 #include "libavutil/common.h"
28 
36 
37 #define WIN_FUNC_OPTION(win_func_opt_name, win_func_offset, flag, default_window_func) \
38  { win_func_opt_name, "set window function", win_func_offset, AV_OPT_TYPE_INT, {.i64 = default_window_func}, 0, NB_WFUNC-1, flag, .unit = "win_func" }, \
39  { "rect", "Rectangular", 0, AV_OPT_TYPE_CONST, {.i64=WFUNC_RECT}, 0, 0, flag, .unit = "win_func" }, \
40  { "bartlett", "Bartlett", 0, AV_OPT_TYPE_CONST, {.i64=WFUNC_BARTLETT}, 0, 0, flag, .unit = "win_func" }, \
41  { "hann", "Hann", 0, AV_OPT_TYPE_CONST, {.i64=WFUNC_HANNING}, 0, 0, flag, .unit = "win_func" }, \
42  { "hanning", "Hanning", 0, AV_OPT_TYPE_CONST, {.i64=WFUNC_HANNING}, 0, 0, flag, .unit = "win_func" }, \
43  { "hamming", "Hamming", 0, AV_OPT_TYPE_CONST, {.i64=WFUNC_HAMMING}, 0, 0, flag, .unit = "win_func" }, \
44  { "blackman", "Blackman", 0, AV_OPT_TYPE_CONST, {.i64=WFUNC_BLACKMAN}, 0, 0, flag, .unit = "win_func" }, \
45  { "welch", "Welch", 0, AV_OPT_TYPE_CONST, {.i64=WFUNC_WELCH}, 0, 0, flag, .unit = "win_func" }, \
46  { "flattop", "Flat-top", 0, AV_OPT_TYPE_CONST, {.i64=WFUNC_FLATTOP}, 0, 0, flag, .unit = "win_func" }, \
47  { "bharris", "Blackman-Harris", 0, AV_OPT_TYPE_CONST, {.i64=WFUNC_BHARRIS}, 0, 0, flag, .unit = "win_func" }, \
48  { "bnuttall", "Blackman-Nuttall", 0, AV_OPT_TYPE_CONST, {.i64=WFUNC_BNUTTALL}, 0, 0, flag, .unit = "win_func" }, \
49  { "bhann", "Bartlett-Hann", 0, AV_OPT_TYPE_CONST, {.i64=WFUNC_BHANN}, 0, 0, flag, .unit = "win_func" }, \
50  { "sine", "Sine", 0, AV_OPT_TYPE_CONST, {.i64=WFUNC_SINE}, 0, 0, flag, .unit = "win_func" }, \
51  { "nuttall", "Nuttall", 0, AV_OPT_TYPE_CONST, {.i64=WFUNC_NUTTALL}, 0, 0, flag, .unit = "win_func" }, \
52  { "lanczos", "Lanczos", 0, AV_OPT_TYPE_CONST, {.i64=WFUNC_LANCZOS}, 0, 0, flag, .unit = "win_func" }, \
53  { "gauss", "Gauss", 0, AV_OPT_TYPE_CONST, {.i64=WFUNC_GAUSS}, 0, 0, flag, .unit = "win_func" }, \
54  { "tukey", "Tukey", 0, AV_OPT_TYPE_CONST, {.i64=WFUNC_TUKEY}, 0, 0, flag, .unit = "win_func" }, \
55  { "dolph", "Dolph-Chebyshev", 0, AV_OPT_TYPE_CONST, {.i64=WFUNC_DOLPH}, 0, 0, flag, .unit = "win_func" }, \
56  { "cauchy", "Cauchy", 0, AV_OPT_TYPE_CONST, {.i64=WFUNC_CAUCHY}, 0, 0, flag, .unit = "win_func" }, \
57  { "parzen", "Parzen", 0, AV_OPT_TYPE_CONST, {.i64=WFUNC_PARZEN}, 0, 0, flag, .unit = "win_func" }, \
58  { "poisson", "Poisson", 0, AV_OPT_TYPE_CONST, {.i64=WFUNC_POISSON}, 0, 0, flag, .unit = "win_func" }, \
59  { "bohman", "Bohman", 0, AV_OPT_TYPE_CONST, {.i64=WFUNC_BOHMAN}, 0, 0, flag, .unit = "win_func" }, \
60  { "kaiser", "Kaiser", 0, AV_OPT_TYPE_CONST, {.i64=WFUNC_KAISER}, 0, 0, flag, .unit = "win_func" }
61 
62 
63 static inline void generate_window_func(float *lut, int N, int win_func,
64  float *overlap)
65 {
66  int n;
67 
68  switch (win_func) {
69  case WFUNC_RECT:
70  for (n = 0; n < N; n++)
71  lut[n] = 1.;
72  *overlap = 0.;
73  break;
74  case WFUNC_BARTLETT:
75  for (n = 0; n < N; n++)
76  lut[n] = 1.-fabs((n-(N-1)/2.)/((N-1)/2.));
77  *overlap = 0.5;
78  break;
79  case WFUNC_HANNING:
80  for (n = 0; n < N; n++)
81  lut[n] = .5*(1-cos(2*M_PI*n/(N-1)));
82  *overlap = 0.5;
83  break;
84  case WFUNC_HAMMING:
85  for (n = 0; n < N; n++)
86  lut[n] = .54-.46*cos(2*M_PI*n/(N-1));
87  *overlap = 0.5;
88  break;
89  case WFUNC_BLACKMAN:
90  for (n = 0; n < N; n++)
91  lut[n] = .42659-.49656*cos(2*M_PI*n/(N-1))+.076849*cos(4*M_PI*n/(N-1));
92  *overlap = 0.661;
93  break;
94  case WFUNC_WELCH:
95  for (n = 0; n < N; n++)
96  lut[n] = 1.-(n-(N-1)/2.)/((N-1)/2.)*(n-(N-1)/2.)/((N-1)/2.);
97  *overlap = 0.293;
98  break;
99  case WFUNC_FLATTOP:
100  for (n = 0; n < N; n++)
101  lut[n] = 1.-1.985844164102*cos( 2*M_PI*n/(N-1))+1.791176438506*cos( 4*M_PI*n/(N-1))-
102  1.282075284005*cos( 6*M_PI*n/(N-1))+0.667777530266*cos( 8*M_PI*n/(N-1))-
103  0.240160796576*cos(10*M_PI*n/(N-1))+0.056656381764*cos(12*M_PI*n/(N-1))-
104  0.008134974479*cos(14*M_PI*n/(N-1))+0.000624544650*cos(16*M_PI*n/(N-1))-
105  0.000019808998*cos(18*M_PI*n/(N-1))+0.000000132974*cos(20*M_PI*n/(N-1));
106  *overlap = 0.841;
107  break;
108  case WFUNC_BHARRIS:
109  for (n = 0; n < N; n++)
110  lut[n] = 0.35875-0.48829*cos(2*M_PI*n/(N-1))+0.14128*cos(4*M_PI*n/(N-1))-0.01168*cos(6*M_PI*n/(N-1));
111  *overlap = 0.661;
112  break;
113  case WFUNC_BNUTTALL:
114  for (n = 0; n < N; n++)
115  lut[n] = 0.3635819-0.4891775*cos(2*M_PI*n/(N-1))+0.1365995*cos(4*M_PI*n/(N-1))-0.0106411*cos(6*M_PI*n/(N-1));
116  *overlap = 0.661;
117  break;
118  case WFUNC_BHANN:
119  for (n = 0; n < N; n++)
120  lut[n] = 0.62-0.48*fabs(n/(double)(N-1)-.5)-0.38*cos(2*M_PI*n/(N-1));
121  *overlap = 0.5;
122  break;
123  case WFUNC_SINE:
124  for (n = 0; n < N; n++)
125  lut[n] = sin(M_PI*n/(N-1));
126  *overlap = 0.75;
127  break;
128  case WFUNC_NUTTALL:
129  for (n = 0; n < N; n++)
130  lut[n] = 0.355768-0.487396*cos(2*M_PI*n/(N-1))+0.144232*cos(4*M_PI*n/(N-1))-0.012604*cos(6*M_PI*n/(N-1));
131  *overlap = 0.663;
132  break;
133  case WFUNC_LANCZOS:
134  #define SINC(x) (!(x)) ? 1 : sin(M_PI * (x))/(M_PI * (x));
135  for (n = 0; n < N; n++)
136  lut[n] = SINC((2.*n)/(N-1)-1);
137  *overlap = 0.75;
138  break;
139  case WFUNC_GAUSS:
140  #define SQR(x) ((x)*(x))
141  for (n = 0; n < N; n++)
142  lut[n] = exp(-0.5 * SQR((n-(N-1)/2)/(0.4*(N-1)/2.f)));
143  *overlap = 0.75;
144  break;
145  case WFUNC_TUKEY:
146  for (n = 0; n < N; n++) {
147  float M = (N-1)/2.;
148 
149  if (FFABS(n - M) >= 0.3 * M) {
150  lut[n] = 0.5 * (1 + cos((M_PI*(FFABS(n - M) - 0.3 * M))/((1 - 0.3) * M)));
151  } else {
152  lut[n] = 1;
153  }
154  }
155  *overlap = 0.33;
156  break;
157  case WFUNC_DOLPH: {
158  double b = cosh(7.6009022095419887 / (N-1)), sum, t, c, norm = 0;
159  int j;
160  for (c = 1 - 1 / (b*b), n = (N-1) / 2; n >= 0; --n) {
161  for (sum = !n, b = t = j = 1; j <= n && sum != t; b *= (n-j) * (1./j), ++j)
162  t = sum, sum += (b *= c * (N - n - j) * (1./j));
163  sum /= (N - 1 - n), norm = norm ? norm : sum, sum /= norm;
164  lut[n] = sum;
165  lut[N - 1 - n] = sum;
166  }
167  *overlap = 0.5;}
168  break;
169  case WFUNC_CAUCHY:
170  for (n = 0; n < N; n++) {
171  double x = 2 * ((n / (double)(N - 1)) - .5);
172 
173  if (x <= -.5 || x >= .5) {
174  lut[n] = 0;
175  } else {
176  lut[n] = FFMIN(1, fabs(1/(1+4*16*x*x)));
177  }
178  }
179  *overlap = 0.75;
180  break;
181  case WFUNC_PARZEN:
182  for (n = 0; n < N; n++) {
183  double x = 2 * ((n / (double)(N - 1)) - .5);
184 
185  if (x > 0.25 && x <= 0.5) {
186  lut[n] = -2 * powf(-1 + 2 * x, 3);
187  } else if (x >= -.5 && x < -.25) {
188  lut[n] = 2 * powf(1 + 2 * x, 3);
189  } else if (x >= -.25 && x < 0) {
190  lut[n] = 1 - 24 * x * x - 48 * x * x * x;
191  } else if (x >= 0 && x <= .25) {
192  lut[n] = 1 - 24 * x * x + 48 * x * x * x;
193  } else {
194  lut[n] = 0;
195  }
196  }
197  *overlap = 0.75;
198  break;
199  case WFUNC_POISSON:
200  for (n = 0; n < N; n++) {
201  double x = 2 * ((n / (double)(N - 1)) - .5);
202 
203  if (x >= 0 && x <= .5) {
204  lut[n] = exp(-6*x);
205  } else if (x < 0 && x >= -.5) {
206  lut[n] = exp(6*x);
207  } else {
208  lut[n] = 0;
209  }
210  }
211  *overlap = 0.75;
212  break;
213  case WFUNC_BOHMAN:
214  for (n = 0; n < N; n++) {
215  double x = 2 * ((n / (double)(N - 1))) - 1.;
216 
217  lut[n] = (1 - fabs(x)) * cos(M_PI*fabs(x)) + 1./M_PI*sin(M_PI*fabs(x));
218  }
219  *overlap = 0.75;
220  break;
221  case WFUNC_KAISER:
222  {
223  double scale = 1.0 / av_bessel_i0(12.);
224  for (n = 0; n < N; n++) {
225  double x = 2.0 / (double)(N - 1);
226  lut[n] = av_bessel_i0(12. * sqrt(1. - SQR(n * x - 1.))) * scale;
227  }
228  *overlap = 0.75;
229  break;
230  }
231  default:
232  av_assert0(0);
233  }
234 }
235 
236 #endif /* AVFILTER_WINDOW_FUNC_H */
M
#define M(a, b)
Definition: vp3dsp.c:48
av_bessel_i0
double av_bessel_i0(double x)
0th order modified bessel function of the first kind.
Definition: mathematics.c:257
b
#define b
Definition: input.c:41
WFUNC_BNUTTALL
@ WFUNC_BNUTTALL
Definition: window_func.h:31
WFUNC_KAISER
@ WFUNC_KAISER
Definition: window_func.h:34
WFUNC_FLATTOP
@ WFUNC_FLATTOP
Definition: window_func.h:30
WFUNC_HAMMING
@ WFUNC_HAMMING
Definition: window_func.h:29
WFUNC_PARZEN
@ WFUNC_PARZEN
Definition: window_func.h:33
WindowFunc
WindowFunc
Definition: af_firequalizer.c:35
WFUNC_TUKEY
@ WFUNC_TUKEY
Definition: window_func.h:32
WFUNC_BHANN
@ WFUNC_BHANN
Definition: window_func.h:32
avassert.h
WFUNC_DOLPH
@ WFUNC_DOLPH
Definition: window_func.h:33
WFUNC_BHARRIS
@ WFUNC_BHARRIS
Definition: window_func.h:31
av_assert0
#define av_assert0(cond)
assert() equivalent, that is always enabled.
Definition: avassert.h:40
WFUNC_LANCZOS
@ WFUNC_LANCZOS
Definition: window_func.h:32
WFUNC_RECT
@ WFUNC_RECT
Definition: window_func.h:29
FFABS
#define FFABS(a)
Absolute value, Note, INT_MIN / INT64_MIN result in undefined behavior as they are not representable ...
Definition: common.h:74
NB_WFUNC
@ NB_WFUNC
Definition: window_func.h:35
fabs
static __device__ float fabs(float a)
Definition: cuda_runtime.h:182
double
double
Definition: af_crystalizer.c:132
generate_window_func
static void generate_window_func(float *lut, int N, int win_func, float *overlap)
Definition: window_func.h:63
WFUNC_HANNING
@ WFUNC_HANNING
Definition: window_func.h:29
WFUNC_BARTLETT
@ WFUNC_BARTLETT
Definition: window_func.h:30
WFUNC_BOHMAN
@ WFUNC_BOHMAN
Definition: window_func.h:34
exp
int8_t exp
Definition: eval.c:73
c
Undefined Behavior In the C some operations are like signed integer dereferencing freed accessing outside allocated Undefined Behavior must not occur in a C it is not safe even if the output of undefined operations is unused The unsafety may seem nit picking but Optimizing compilers have in fact optimized code on the assumption that no undefined Behavior occurs Optimizing code based on wrong assumptions can and has in some cases lead to effects beyond the output of computations The signed integer overflow problem in speed critical code Code which is highly optimized and works with signed integers sometimes has the problem that often the output of the computation does not c
Definition: undefined.txt:32
f
f
Definition: af_crystalizer.c:122
powf
#define powf(x, y)
Definition: libm.h:50
N
#define N
Definition: af_mcompand.c:54
M_PI
#define M_PI
Definition: mathematics.h:67
common.h
FFMIN
#define FFMIN(a, b)
Definition: macros.h:49
WFUNC_SINE
@ WFUNC_SINE
Definition: window_func.h:31
WFUNC_CAUCHY
@ WFUNC_CAUCHY
Definition: window_func.h:33
WFUNC_GAUSS
@ WFUNC_GAUSS
Definition: window_func.h:32
WFUNC_NUTTALL
@ WFUNC_NUTTALL
Definition: window_func.h:31
WFUNC_POISSON
@ WFUNC_POISSON
Definition: window_func.h:33
SQR
#define SQR(x)
scale
static void scale(int *out, const int *in, const int w, const int h, const int shift)
Definition: intra.c:291
SINC
#define SINC(x)
WFUNC_BLACKMAN
@ WFUNC_BLACKMAN
Definition: window_func.h:29
WFUNC_WELCH
@ WFUNC_WELCH
Definition: window_func.h:30