dsplib 1.1.0
C++ DSP library for MATLAB-like coding
Loading...
Searching...
No Matches
noise-gate.h
1#pragma once
2
3#include <dsplib/math.h>
4#include <dsplib/array.h>
5
6namespace dsplib {
7
8//Dynamic range gate
10{
11public:
12 explicit NoiseGate(int sample_rate = 44100, real_t threshold = -10.0, real_t attack_time = 0.05,
13 real_t release_time = 0.02, real_t hold_time = 0.05)
14 : tlin_{db2mag(threshold)}
15 , wA_{std::exp(-std::log(real_t(9)) / (sample_rate * attack_time))}
16 , wR_{std::exp(-std::log(real_t(9)) / (sample_rate * release_time))}
17 , tH_{int(std::floor(hold_time * sample_rate))} {
18 DSPLIB_ASSERT(threshold >= -140 && threshold <= 0, "`threshold` must be in range [-140:0] db");
19 DSPLIB_ASSERT(attack_time >= 0 && attack_time <= 4, "`attack_time` must be in range [0:4] sec");
20 DSPLIB_ASSERT(release_time >= 0 && release_time <= 4, "`release_time` must be in range [0:4] sec");
21 DSPLIB_ASSERT(hold_time >= 0 && hold_time <= 4, "`hold_time` must be in range [0:4] sec");
22 }
23
24 struct Result
25 {
26 explicit Result(int n)
27 : out(n)
28 , gain(n) {
29 }
30 arr_real out;
31 arr_real gain;
32 };
33
34 Result process(const arr_real& x) {
35 const int n = x.size();
36 Result res(n);
37 for (int i = 0; i < n; ++i) {
38 const auto gc = (dsplib::abs(x[i]) >= tlin_) ? 1 : 0;
39 lg_ = _smooth_gain(gc);
40 res.gain[i] = lg_;
41 res.out[i] = x[i] * res.gain[i];
42 }
43 return res;
44 }
45
46 Result operator()(const arr_real& x) {
47 return this->process(x);
48 }
49
50private:
51 real_t _smooth_gain(real_t gc) noexcept {
52 if (gc == lg_) {
53 return gc;
54 }
55
56 //attack
57 if (gc < lg_) {
58 if (cA_ < tH_) {
59 cA_ += 1;
60 return lg_;
61 } else {
62 return (wA_ * lg_) + ((1 - wA_) * gc);
63 }
64 } else {
65 //release
66 cA_ = 0;
67 return (wR_ * lg_) + ((1 - wR_) * gc);
68 }
69
70 return lg_;
71 }
72
73 real_t tlin_;
74 real_t wA_;
75 real_t wR_;
76 int tH_;
77 int cA_{0};
78 real_t lg_{0};
79};
80
81} // namespace dsplib
Definition noise-gate.h:10
Definition noise-gate.h:25