1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
ix!();
use crate::{
C,
NonlinearFeedbackFilter,
NLFFType,
};
impl CoeffMake for NonlinearFeedbackFilter {
fn coeff_make(&self, freq: f32, mut reso: f32) -> [f32; N_COEFFMAKER_COEFFS] {
let mut coeffs = [0.0_f32; N_COEFFMAKER_COEFFS];
reso = limit_range(reso, 0.0, 1.0);
let q: f32 = (reso * reso * reso) * 18.0 + 0.1;
let normalized_freq: f32 = 2.0 * self.clamped_frequency(freq) / self.srunit.samplerate_os();
let wc: f32 = PI_32 * normalized_freq;
let wsin: f32 = fastsin(wc);
let wcos: f32 = fastcos(wc);
let alpha: f32 = wsin / (2.0 * q);
let a0r: f32 = 1.0 / (1.0 + alpha);
coeffs[C::A1] = -2.0 * wcos * a0r;
coeffs[C::A2] = (1.0 - alpha) * a0r;
coeffs[C::Makeup] = 1.0;
let use_normalization = true;
let mut norm_numerator: f32 = 1.0;
const LP_NORM_TABLE: [f32; 12] = [
1.53273,
1.33407,
1.08197,
0.958219,
1.27374,
0.932342,
0.761765,
0.665462,
0.776856,
0.597575,
0.496207,
0.471714
];
let exp_min: f32 = match self.ty == NLFFType::LowPass {
true => 0.1,
false => 0.35,
};
let res_makeup: f32 = match (self.subty as usize) < 8 {
true => 1.0,
false => {
1.0 / std::cmp::max(FloatOrd(reso), FloatOrd(exp_min)).0.powf(0.5)
},
};
match self.ty {
NLFFType::LowPass => {
coeffs[C::B1] = (1.0 - wcos) * a0r;
coeffs[C::B0] = coeffs[C::B1] * 0.5;
coeffs[C::B2] = coeffs[C::B0];
if use_normalization
{
norm_numerator = LP_NORM_TABLE[self.subty as usize];
}
coeffs[C::Makeup] =
res_makeup * norm_numerator
/ std::cmp::max(
FloatOrd(normalized_freq),
FloatOrd(0.001)
).0.powf(0.1);
},
NLFFType::HighPass => {
coeffs[C::B1] = -(1.0 + wcos) * a0r;
coeffs[C::B0] = coeffs[C::B1] * -0.5;
coeffs[C::B2] = coeffs[C::B0];
if use_normalization
{
norm_numerator = LP_NORM_TABLE[self.subty as usize];
}
coeffs[C::Makeup] =
res_makeup * norm_numerator
/ std::cmp::max(
FloatOrd(1.0 - normalized_freq),
FloatOrd(0.001)
).0.powf(0.1);
},
NLFFType::BandPass => {
coeffs[C::B0] = wsin * 0.5 * a0r;
coeffs[C::B1] = 0.0;
coeffs[C::B2] = -coeffs[C::B0];
},
NLFFType::Notch => {
coeffs[C::B0] = a0r;
coeffs[C::B1] = -2.0 * wcos * a0r;
coeffs[C::B2] = coeffs[C::B0];
},
NLFFType::Allpass => {
coeffs[C::B0] = coeffs[C::A2];
coeffs[C::B1] = coeffs[C::A1];
coeffs[C::B2] = 1.0;
},
}
coeffs
}
}