7 #ifndef ADC_FILTER_HPP__
8 #define ADC_FILTER_HPP__
26 static_assert(N <= 1<<16 && (N & (N-1)) == 0);
47 input_buffer.fill(init_value);
48 result_sum = N * init_value;
56 auto value_out = input_buffer[current_index];
57 input_buffer[current_index] = value_in;
58 current_index = (current_index + 1) % N;
59 result_sum = result_sum + value_in - value_out;
67 return result_sum / N;
71 size_t current_index = 0;
72 std::array<uint16_t, N> input_buffer;
91 int32_t in_fsr_bot = 0,
92 int32_t in_fsr_top = 1)
95 set_input_full_scale_range(in_fsr_bot, in_fsr_top);
98 void set_input_full_scale_range(int32_t in_fsr_bot, int32_t in_fsr_top) {
99 assert(in_fsr_top > in_fsr_bot);
100 _in_fsr_bot = in_fsr_bot;
101 _in_fsr_top = in_fsr_top;
102 _in_fsr_inv = 1.0f / (in_fsr_top - in_fsr_bot);
105 float interpolate(int32_t x) {
106 static_assert(1 < N && N < INT32_MAX,
"Filter length must be in this range");
107 constexpr
auto n_lut_intervals =
size_t{N - 1};
109 float partial_intervals;
110 if (x > _in_fsr_bot) {
111 if (x < _in_fsr_top) {
112 auto n =
static_cast<int64_t
>(n_lut_intervals) * (x - _in_fsr_bot);
113 auto d = _in_fsr_top - _in_fsr_bot;
114 auto quot_rem = lldiv(n, d);
115 partial_intervals = _in_fsr_inv *
static_cast<float>(quot_rem.rem);
116 lut_index =
static_cast<size_t>(quot_rem.quot);
118 lut_index = n_lut_intervals;
119 partial_intervals = 0.0f;
123 partial_intervals = 0.0f;
126 auto interval_start = _lut[lut_index];
128 if (lut_index < n_lut_intervals) {
129 interval_end = _lut[lut_index + 1];
131 interval_end = interval_start;
133 return interval_start + partial_intervals * (interval_end - interval_start);
137 const std::array<float, N> _lut;
158 uint16_t in_fsr_bot = 0,
159 uint16_t in_fsr_top = 1)
162 set_input_full_scale_range(in_fsr_bot, in_fsr_top);
165 void set_input_full_scale_range(uint16_t in_fsr_bot, uint16_t in_fsr_top) {
166 assert(in_fsr_top > in_fsr_bot);
168 _in_fsr_bot = in_fsr_bot;
169 _in_fsr_top = in_fsr_top;
170 _in_fsr_inv = 1.0f / (in_fsr_top - in_fsr_bot);
173 float interpolate(uint16_t x) {
174 static_assert(1 < N && N < INT16_MAX,
"Filter length must be in this range");
175 constexpr
auto n_lut_intervals =
size_t{N - 1};
177 float partial_intervals;
178 if (x > _in_fsr_bot) {
179 if (x < _in_fsr_top) {
180 auto n =
static_cast<int32_t
>(n_lut_intervals) * (x - _in_fsr_bot);
181 auto d = _in_fsr_top - _in_fsr_bot;
182 auto quot_rem = div(n, d);
183 partial_intervals = _in_fsr_inv *
static_cast<float>(quot_rem.rem);
184 lut_index =
static_cast<size_t>(quot_rem.quot);
186 lut_index = n_lut_intervals;
187 partial_intervals = 0.0f;
191 partial_intervals = 0.0f;
194 auto interval_start = _lut[lut_index];
196 if (lut_index < n_lut_intervals) {
197 interval_end = _lut[lut_index + 1];
199 interval_end = interval_start;
201 return interval_start + partial_intervals * (interval_end - interval_start);
205 const std::array<float, N> _lut;
206 uint16_t _in_fsr_bot;
207 uint16_t _in_fsr_top;
226 uint32_t in_fsr_bot = 0,
227 uint32_t in_fsr_top = 1)
230 set_input_full_scale_range(in_fsr_bot, in_fsr_top);
233 void set_input_full_scale_range(uint32_t in_fsr_bot, uint32_t in_fsr_top) {
234 assert(in_fsr_top > in_fsr_bot);
236 _in_fsr_bot = in_fsr_bot;
237 _in_fsr_top = in_fsr_top;
238 _in_fsr_inv = 1.0f / (in_fsr_top - in_fsr_bot);
241 float interpolate(uint32_t x) {
242 static_assert(1 < N && N < INT32_MAX,
"Filter length must be in this range");
243 constexpr
auto n_lut_intervals =
size_t{N - 1};
245 float partial_intervals;
246 if (x > _in_fsr_bot) {
247 if (x < _in_fsr_top) {
248 auto n =
static_cast<int64_t
>(n_lut_intervals) * (x - _in_fsr_bot);
249 auto d = _in_fsr_top - _in_fsr_bot;
250 auto quot_rem = lldiv(n, d);
251 partial_intervals = _in_fsr_inv *
static_cast<float>(quot_rem.rem);
252 lut_index =
static_cast<size_t>(quot_rem.quot);
254 lut_index = n_lut_intervals;
255 partial_intervals = 0.0f;
259 partial_intervals = 0.0f;
262 auto interval_start = _lut[lut_index];
264 if (lut_index < n_lut_intervals) {
265 interval_end = _lut[lut_index + 1];
267 interval_end = interval_start;
269 return interval_start + partial_intervals * (interval_end - interval_start);
273 const std::array<float, N> _lut;
274 uint32_t _in_fsr_bot;
275 uint32_t _in_fsr_top;
Piecewise linear interpolation of look-up-table (LUT) values.
Definition: adc_filter_interpolation.hpp:88
Piecewise linear interpolation of look-up-table (LUT) values.
Definition: adc_filter_interpolation.hpp:155
Piecewise linear interpolation of look-up-table (LUT) values.
Definition: adc_filter_interpolation.hpp:223
Does a recursive moving average over N values.
Definition: adc_filter_interpolation.hpp:23
void input_data(uint16_t value_in)
Read in a new datum and update the filter.
Definition: adc_filter_interpolation.hpp:55
uint16_t get_result()
Get filter output value.
Definition: adc_filter_interpolation.hpp:66
void initialize(uint16_t init_value)
Initializes the moving average filter with a start value.
Definition: adc_filter_interpolation.hpp:46