blob: 2e0e3bcae0fbd980aede1c7915e8c16e7c75a803 [file] [log] [blame]
Austin Schuhc6423e62017-02-11 16:56:30 -08001#include "frc971/zeroing/wrap.h"
2
3#include <cmath>
4
Stephan Pleinesf63bde82024-01-13 15:59:33 -08005namespace frc971::zeroing {
Austin Schuhc6423e62017-02-11 16:56:30 -08006
Stephan Massalt4d1e74f2020-01-11 17:50:39 -08007UnwrapSensor::UnwrapSensor(double sensor_offset, double sensor_range)
8 : sensor_offset_(sensor_offset), sensor_range_(sensor_range) {
9 Reset();
10}
11
12double UnwrapSensor::Unwrap(double current_sensor_value) {
13 // First time the function is called it will use that value to initialize the
14 // wrap calculation. This catches cases where the offset and first value
15 // difference triggers an unwanted wrap at the first calculation.
16 if (uninitialized_ == true) {
17 uninitialized_ = false;
18 } else {
19 // Calculates the lower sensor value and set the max sensor range
20 // If offset is not 0, this will correct the zeroing offset
21 const double sensor_min_value = sensor_offset_;
22 const double sensor_max_value = sensor_range_ + sensor_min_value;
23
24 // Check if provided sensor value is within the range. This to prevent the
25 // function to get out of sync. Will not throw an error, but continue and
26 // return the value + wrapped factor and not process this value.
27 if (current_sensor_value < sensor_min_value ||
28 current_sensor_value > sensor_max_value) {
29 return current_sensor_value + (sensor_range_ * wrap_count_);
30 }
31
32 // Calculate the positive or negative movement
33 const double sensor_move = current_sensor_value - sensor_last_value_;
34
35 // Function assumes that a movement of more then 1/2 of the range
36 // indicates that we wrapped, instead of moved very fast.
37 if (std::abs(sensor_move) > (sensor_range_ / 2)) {
38 if (sensor_move >= 0) {
39 // sensor moved past the sensor_min_value
40 wrap_count_ -= 1;
41 } else {
42 // sensor moved past the sensor_max_value
43 wrap_count_ += 1;
44 }
45 }
46 }
47 sensor_last_value_ = current_sensor_value;
48 // return the unwrapped sensor value
49 return current_sensor_value + (sensor_range_ * wrap_count_);
50}
51
52void UnwrapSensor::Reset() {
53 wrap_count_ = 0;
54 sensor_last_value_ = sensor_offset_;
55 uninitialized_ = true;
56}
57
Austin Schuh4fae0fc2018-03-27 23:51:42 -070058float Wrap(float nearest, float value, float period) {
59 return remainderf(value - nearest, period) + nearest;
60}
61
Austin Schuhc6423e62017-02-11 16:56:30 -080062double Wrap(double nearest, double value, double period) {
Austin Schuh4fae0fc2018-03-27 23:51:42 -070063 return remainder(value - nearest, period) + nearest;
Austin Schuhc6423e62017-02-11 16:56:30 -080064}
65
Stephan Pleinesf63bde82024-01-13 15:59:33 -080066} // namespace frc971::zeroing