5#include "TinyRobotics/communication/Message.h"
6#include "TinyRobotics/communication/MessageSource.h"
7#include "TinyRobotics/control/Scheduler.h"
8#include "TinyRobotics/odometry/ISpeedSource.h"
9#include "TinyRobotics/units/Distance.h"
10#include "TinyRobotics/units/Units.h"
12namespace tinyrobotics {
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
72
73
74
83
84
85
86
87
96
97
98
100 wheelDiameterM = wheelDiameter.getValue(
DistanceUnit::M);
104
105
106
107
113
114
115
117 ticksPerRevolution = ticks;
119 static_cast<
float>(M_PI) * wheelDiameterM / ticksPerRevolution;
123
124
125
131
132
133
137
138
139
141 if (motor >= numWheels)
return 0.0f;
142 return distanceM[motor] * slipFactor;
146
147
148
149
151 Distance dist(getDistanceM(motor), DistanceUnit::M);
152 return dist.getValue(unit);
156
157
158
159
160
162 return ticks * distancePerTickM;
166
167
168
169
170
172 Distance dist(getDistanceForTicksM(ticks), DistanceUnit::M);
173 return dist.getValue(unit);
177
178
179
180
181
182
184 distanceM.resize(numWheels, 0.0f);
185 lastSpeedCalcTimeMs.resize(numWheels, 0);
186 lastDistanceM.resize(numWheels, 0.0f);
187 speedMPS.resize(numWheels, 0.0f);
188 for (size_t i = 0; i < numWheels; ++i) {
190 lastSpeedCalcTimeMs[i] = millis();
191 lastDistanceM[i] = 0;
194 if (!reportingScheduler.isActive()) {
197 return wheelDiameterM > 0 && ticksPerRevolution > 0;
201
202
203
204
205 void setTick(size_t motor = 0) {
206 if (motor >= numWheels)
return;
207 distanceM[motor] += distancePerTickM;
208 reportingScheduler.run();
221 return Speed(speedMPS[motor], SpeedUnit::MPS);
225
226
227
228
230 for (size_t i = 0; i < numWheels; ++i) {
231 Message<
float> msg(MessageContent::Distance, getDistanceM(i),
233 msg.origin = MessageOrigin::Sensor;
234 MessageSource::sendMessage(msg);
236 Message<
float> speedMsg(MessageContent::Speed, getSpeedMPS(i),
237 Unit::MetersPerSecond);
238 speedMsg.origin = MessageOrigin::Sensor;
239 MessageSource::sendMessage(speedMsg);
244
245
246
247
248
249
250
251 void setSlipFactor(
float slipFactor) {
this->slipFactor = slipFactor; }
254
255
256
257
258
259
261 float encoderDistance = getRawDistanceM();
262 if (encoderDistance > 0) {
263 slipFactor = actualDistanceM / encoderDistance;
268
269
270
274
275
276
278 if (motor >= numWheels)
return 0.0f;
279 return distanceM[motor];
285 size_t getMotorCount()
const override {
return numWheels; }
288 std::vector<
float> speedMPS;
289 std::vector<
float> distanceM;
291 Distance getDistance(size_t motor = 0)
const {
293 return Distance(distanceM[motor], DistanceUnit::M);
295 float wheelDiameterM = 0.0f;
296 float distancePerTickM = 0.0f;
297 std::vector<
float> lastDistanceM;
298 float slipFactor = 1.0f;
299 uint32_t ticksPerRevolution = 0;
300 std::vector<uint32_t> lastSpeedCalcTimeMs;
302 size_t numWheels = 1;
305
306
307
314
315
316
317
319 if (motor >= numWheels)
return 0.0f;
321 uint32_t currentTimeMs = millis();
322 uint32_t elapsedTimeMs = currentTimeMs - lastSpeedCalcTimeMs[motor];
323 if (elapsedTimeMs > 0) {
324 float distanceTraveledM =
325 (distanceM[motor] - lastDistanceM[motor]) * slipFactor;
326 speedMPS[motor] = distanceTraveledM / (elapsedTimeMs / 1000.0f);
327 lastSpeedCalcTimeMs[motor] = currentTimeMs;
328 lastDistanceM[motor] = distanceM[motor];
330 return speedMPS[motor];
Represents a distance measurement with unit conversion support.
Definition: Distance.h:40
Interface for speed sources.
Definition: ISpeedSource.h:9
Base class for message sources in the TinyRobotics communication framework.
Definition: MessageSource.h:35
Simple periodic task scheduler for embedded and Arduino environments.
Definition: Scheduler.h:57
Represents a speed measurement with unit conversion support.
Definition: Speed.h:40
Measures wheel rotation and computes per-wheel distance and speed using encoder ticks for mobile robo...
Definition: WheelEncoder.h:69
void setSlipFactor(float slipFactor)
Set the slip correction factor.
Definition: WheelEncoder.h:251
static void sendMessageCB(void *ref)
Static callback for the reporting scheduler to send messages.
Definition: WheelEncoder.h:308
float getDistanceM(size_t motor=0) const
Get the total distance traveled since last reset.
Definition: WheelEncoder.h:140
float getDistance(DistanceUnit unit, size_t motor=0) const
Get the total distance traveled in the specified unit.
Definition: WheelEncoder.h:150
void setWheelDiameter(float diameter, DistanceUnit unit=DistanceUnit::M)
Set the wheel diameter using a float value and unit.
Definition: WheelEncoder.h:108
WheelEncoder(Distance wheelDiameterM, int ticksPerRevolution=1, size_t numWheels=1)
Constructor with wheel diameter and ticks per revolution.
Definition: WheelEncoder.h:88
bool begin()
Resets the encoder counts and distance.
Definition: WheelEncoder.h:183
float getSlipFactor() const
Get the slip correction factor.
Definition: WheelEncoder.h:271
Speed getSpeed(uint8_t motor=0) const override
Get the current speed.
Definition: WheelEncoder.h:211
void setThrottlePercent(float value, uint8_t motor=0) override
Not used.
Definition: WheelEncoder.h:283
void setReportingFrequencyMs(uint16_t ms)
Defines the reporint frequency for distance and speed messages.
Definition: WheelEncoder.h:126
Speed updateSpeed(uint32_t deltaTimeMs, uint8_t motor=0) override
Just provide the last reported speed without inertia modeling.
Definition: WheelEncoder.h:219
float getDistanceForTicks(size_t ticks, DistanceUnit unit) const
Get the distance for a given number of ticks in the specified unit.
Definition: WheelEncoder.h:171
float getRawDistanceM(size_t motor=0) const
Get the raw (uncorrected) distance in meters from the encoder.
Definition: WheelEncoder.h:277
float getSpeedMPS(size_t motor=0)
Calculate speed in meters per second based on distance traveled since last calculation and elapsed ti...
Definition: WheelEncoder.h:318
float getDistanceForTicksM(size_t ticks) const
Get the distance corresponding to a given number of ticks (in meters).
Definition: WheelEncoder.h:161
void setTick(size_t motor=0)
To be called by the pin interrupt handler when a tick is detected.
Definition: WheelEncoder.h:205
void sendMessage()
Trigger sending messages for distance and speed.
Definition: WheelEncoder.h:229
void setTicksPerRevolution(int ticks)
Set the number of encoder ticks per wheel revolution.
Definition: WheelEncoder.h:116
void calibrateSlip(float actualDistanceM)
Calibrate slip by providing a known actual distance.
Definition: WheelEncoder.h:260
void setWheelDiameter(Distance wheelDiameter)
Set the wheel diameter using a Distance object.
Definition: WheelEncoder.h:99
WheelEncoder(size_t numWheels=1)
Default constructor. Wheel diameter and ticks per revolution must be set before use.
Definition: WheelEncoder.h:75
DistanceUnit
Supported distance units for conversion and representation.
Definition: Distance.h:10
SpeedUnit
Supported speed units for conversion and representation.
Definition: Speed.h:10