1
- use circular_queue:: CircularQueue ;
2
1
use rand:: { rngs:: SmallRng , SeedableRng } ;
3
2
use rand_distr:: { Distribution , Triangular , Uniform } ;
3
+ use ringbuf:: storage:: Heap ;
4
+ use ringbuf:: traits:: * ;
5
+ use ringbuf:: LocalRb ;
4
6
5
7
use crate :: { config, filters:: Filter , NewValue , PrcFmt , Res } ;
6
8
@@ -14,17 +16,16 @@ pub struct Dither<'a> {
14
16
shaper : Option < NoiseShaper < ' a > > ,
15
17
}
16
18
17
- #[ derive( Clone , Debug ) ]
18
19
pub struct NoiseShaper < ' a > {
19
20
// optimization: lifetime allows taking coefficients
20
21
// from an array instead of allocating a `Vec`.
21
22
filter : & ' a [ PrcFmt ] ,
22
- buffer : CircularQueue < PrcFmt > ,
23
+ buffer : LocalRb < Heap < PrcFmt > > ,
23
24
}
24
25
25
26
impl < ' a > NoiseShaper < ' a > {
26
27
pub fn new ( filter : & ' a [ PrcFmt ] ) -> Self {
27
- let buffer = CircularQueue :: with_capacity ( filter. len ( ) ) ;
28
+ let buffer = LocalRb :: new ( filter. len ( ) ) ;
28
29
Self { filter, buffer }
29
30
}
30
31
@@ -438,15 +439,15 @@ impl<'a> NoiseShaper<'a> {
438
439
439
440
pub fn process ( & mut self , scaled : PrcFmt , dither : PrcFmt ) -> PrcFmt {
440
441
let mut filt_buf = 0.0 ;
441
- for ( item, coeff) in self . buffer . iter ( ) . zip ( self . filter ) {
442
+ for ( item, coeff) in self . buffer . iter ( ) . zip ( self . filter . iter ( ) . rev ( ) ) {
442
443
filt_buf += coeff * item;
443
444
}
444
445
445
446
let scaled_plus_err = scaled + filt_buf;
446
447
let result = scaled_plus_err + dither;
447
448
let result_r = result. round ( ) ; // away from zero
448
449
449
- self . buffer . push ( scaled_plus_err - result_r) ;
450
+ self . buffer . push_overwrite ( scaled_plus_err - result_r) ;
450
451
451
452
result_r
452
453
}
0 commit comments