2 * Copyright (C) 2004 Alex Beregszaszi & Pierre Lombard
4 * This file is part of MPlayer.
6 * MPlayer is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 2 of the License, or
9 * (at your option) any later version.
11 * MPlayer 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
14 * GNU General Public License for more details.
16 * You should have received a copy of the GNU General Public License along
17 * with MPlayer; if not, write to the Free Software Foundation, Inc.,
18 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
32 // 1: uses a 1 value memory and coefficients new=a*old+b*cur (with a+b=1)
33 // 2: uses several samples to smooth the variations (standard weighted mean
36 // Size of the memory array
37 // FIXME: should depend on the frequency of the data (should be a few seconds)
40 // If summing all the mem[].len is lower than MIN_SAMPLE_SIZE bytes, then we
41 // choose to ignore the computed value as it's not significant enough
42 // FIXME: should depend on the frequency of the data (0.5s maybe)
43 #define MIN_SAMPLE_SIZE 32000
45 // mul is the value by which the samples are scaled
46 // and has to be in [MUL_MIN, MUL_MAX]
52 // FIXME: should be relative to the level of the samples
53 #define SIL_S16 (SHRT_MAX * 0.01)
54 #define SIL_FLOAT 0.01
56 // smooth must be in ]0.0, 1.0[
57 #define SMOOTH_MUL 0.06
58 #define SMOOTH_LASTAVG 0.06
60 #define DEFAULT_TARGET 0.25
62 // Data for specific instances of this filter
63 typedef struct af_volume_s
65 int method
; // method used
68 float lastavg
; // history value of the filter
72 float avg
; // average level of the sample
73 int len
; // sample size (weight)
80 // Initialization and runtime control
81 static int control(struct af_instance_s
* af
, int cmd
, void* arg
)
83 af_volnorm_t
* s
= (af_volnorm_t
*)af
->setup
;
86 case AF_CONTROL_REINIT
:
88 if(!arg
) return AF_ERROR
;
90 af
->data
->rate
= ((af_data_t
*)arg
)->rate
;
91 af
->data
->nch
= ((af_data_t
*)arg
)->nch
;
93 if(((af_data_t
*)arg
)->format
== (AF_FORMAT_S16_NE
)){
94 af
->data
->format
= AF_FORMAT_S16_NE
;
97 af
->data
->format
= AF_FORMAT_FLOAT_NE
;
100 return af_test_output(af
,(af_data_t
*)arg
);
101 case AF_CONTROL_COMMAND_LINE
:{
103 float target
= DEFAULT_TARGET
;
104 sscanf((char*)arg
,"%d:%f", &i
, &target
);
105 if (i
!= 1 && i
!= 2)
108 s
->mid_s16
= ((float)SHRT_MAX
) * target
;
109 s
->mid_float
= target
;
117 static void uninit(struct af_instance_s
* af
)
123 static void method1_int16(af_volnorm_t
*s
, af_data_t
*c
)
126 int16_t *data
= (int16_t*)c
->audio
; // Audio data
127 int len
= c
->len
/2; // Number of samples
128 float curavg
= 0.0, newavg
, neededmul
;
131 for (i
= 0; i
< len
; i
++)
136 curavg
= sqrt(curavg
/ (float) len
);
138 // Evaluate an adequate 'mul' coefficient based on previous state, current
139 // samples level, etc
141 if (curavg
> SIL_S16
)
143 neededmul
= s
->mid_s16
/ (curavg
* s
->mul
);
144 s
->mul
= (1.0 - SMOOTH_MUL
) * s
->mul
+ SMOOTH_MUL
* neededmul
;
146 // clamp the mul coefficient
147 s
->mul
= clamp(s
->mul
, MUL_MIN
, MUL_MAX
);
150 // Scale & clamp the samples
151 for (i
= 0; i
< len
; i
++)
153 tmp
= s
->mul
* data
[i
];
154 tmp
= clamp(tmp
, SHRT_MIN
, SHRT_MAX
);
158 // Evaulation of newavg (not 100% accurate because of values clamping)
159 newavg
= s
->mul
* curavg
;
161 // Stores computed values for future smoothing
162 s
->lastavg
= (1.0 - SMOOTH_LASTAVG
) * s
->lastavg
+ SMOOTH_LASTAVG
* newavg
;
165 static void method1_float(af_volnorm_t
*s
, af_data_t
*c
)
168 float *data
= (float*)c
->audio
; // Audio data
169 int len
= c
->len
/4; // Number of samples
170 float curavg
= 0.0, newavg
, neededmul
, tmp
;
172 for (i
= 0; i
< len
; i
++)
177 curavg
= sqrt(curavg
/ (float) len
);
179 // Evaluate an adequate 'mul' coefficient based on previous state, current
180 // samples level, etc
182 if (curavg
> SIL_FLOAT
) // FIXME
184 neededmul
= s
->mid_float
/ (curavg
* s
->mul
);
185 s
->mul
= (1.0 - SMOOTH_MUL
) * s
->mul
+ SMOOTH_MUL
* neededmul
;
187 // clamp the mul coefficient
188 s
->mul
= clamp(s
->mul
, MUL_MIN
, MUL_MAX
);
191 // Scale & clamp the samples
192 for (i
= 0; i
< len
; i
++)
195 // Evaulation of newavg (not 100% accurate because of values clamping)
196 newavg
= s
->mul
* curavg
;
198 // Stores computed values for future smoothing
199 s
->lastavg
= (1.0 - SMOOTH_LASTAVG
) * s
->lastavg
+ SMOOTH_LASTAVG
* newavg
;
202 static void method2_int16(af_volnorm_t
*s
, af_data_t
*c
)
205 int16_t *data
= (int16_t*)c
->audio
; // Audio data
206 int len
= c
->len
/2; // Number of samples
207 float curavg
= 0.0, newavg
, avg
= 0.0;
208 int tmp
, totallen
= 0;
210 for (i
= 0; i
< len
; i
++)
215 curavg
= sqrt(curavg
/ (float) len
);
217 // Evaluate an adequate 'mul' coefficient based on previous state, current
218 // samples level, etc
219 for (i
= 0; i
< NSAMPLES
; i
++)
221 avg
+= s
->mem
[i
].avg
* (float)s
->mem
[i
].len
;
222 totallen
+= s
->mem
[i
].len
;
225 if (totallen
> MIN_SAMPLE_SIZE
)
227 avg
/= (float)totallen
;
230 s
->mul
= s
->mid_s16
/ avg
;
231 s
->mul
= clamp(s
->mul
, MUL_MIN
, MUL_MAX
);
235 // Scale & clamp the samples
236 for (i
= 0; i
< len
; i
++)
238 tmp
= s
->mul
* data
[i
];
239 tmp
= clamp(tmp
, SHRT_MIN
, SHRT_MAX
);
243 // Evaulation of newavg (not 100% accurate because of values clamping)
244 newavg
= s
->mul
* curavg
;
246 // Stores computed values for future smoothing
247 s
->mem
[s
->idx
].len
= len
;
248 s
->mem
[s
->idx
].avg
= newavg
;
249 s
->idx
= (s
->idx
+ 1) % NSAMPLES
;
252 static void method2_float(af_volnorm_t
*s
, af_data_t
*c
)
255 float *data
= (float*)c
->audio
; // Audio data
256 int len
= c
->len
/4; // Number of samples
257 float curavg
= 0.0, newavg
, avg
= 0.0, tmp
;
260 for (i
= 0; i
< len
; i
++)
265 curavg
= sqrt(curavg
/ (float) len
);
267 // Evaluate an adequate 'mul' coefficient based on previous state, current
268 // samples level, etc
269 for (i
= 0; i
< NSAMPLES
; i
++)
271 avg
+= s
->mem
[i
].avg
* (float)s
->mem
[i
].len
;
272 totallen
+= s
->mem
[i
].len
;
275 if (totallen
> MIN_SAMPLE_SIZE
)
277 avg
/= (float)totallen
;
278 if (avg
>= SIL_FLOAT
)
280 s
->mul
= s
->mid_float
/ avg
;
281 s
->mul
= clamp(s
->mul
, MUL_MIN
, MUL_MAX
);
285 // Scale & clamp the samples
286 for (i
= 0; i
< len
; i
++)
289 // Evaulation of newavg (not 100% accurate because of values clamping)
290 newavg
= s
->mul
* curavg
;
292 // Stores computed values for future smoothing
293 s
->mem
[s
->idx
].len
= len
;
294 s
->mem
[s
->idx
].avg
= newavg
;
295 s
->idx
= (s
->idx
+ 1) % NSAMPLES
;
298 // Filter data through filter
299 static af_data_t
* play(struct af_instance_s
* af
, af_data_t
* data
)
301 af_volnorm_t
*s
= af
->setup
;
303 if(af
->data
->format
== (AF_FORMAT_S16_NE
))
306 method2_int16(s
, data
);
308 method1_int16(s
, data
);
310 else if(af
->data
->format
== (AF_FORMAT_FLOAT_NE
))
313 method2_float(s
, data
);
315 method1_float(s
, data
);
320 // Allocate memory and set function pointers
321 static int af_open(af_instance_t
* af
){
327 af
->data
=calloc(1,sizeof(af_data_t
));
328 af
->setup
=calloc(1,sizeof(af_volnorm_t
));
329 if(af
->data
== NULL
|| af
->setup
== NULL
)
332 ((af_volnorm_t
*)af
->setup
)->mul
= MUL_INIT
;
333 ((af_volnorm_t
*)af
->setup
)->lastavg
= ((float)SHRT_MAX
) * DEFAULT_TARGET
;
334 ((af_volnorm_t
*)af
->setup
)->idx
= 0;
335 ((af_volnorm_t
*)af
->setup
)->mid_s16
= ((float)SHRT_MAX
) * DEFAULT_TARGET
;
336 ((af_volnorm_t
*)af
->setup
)->mid_float
= DEFAULT_TARGET
;
337 for (i
= 0; i
< NSAMPLES
; i
++)
339 ((af_volnorm_t
*)af
->setup
)->mem
[i
].len
= 0;
340 ((af_volnorm_t
*)af
->setup
)->mem
[i
].avg
= 0;
345 // Description of this filter
346 af_info_t af_info_volnorm
= {
347 "Volume normalizer filter",
349 "Alex Beregszaszi & Pierre Lombard",
351 AF_FLAGS_NOT_REENTRANT
,