PDController.h
Go to the documentation of this file.
1/*
2 * This file is part of ArmarX.
3 *
4 * ArmarX is free software; you can redistribute it and/or modify
5 * it under the terms of the GNU General Public License version 2 as
6 * published by the Free Software Foundation.
7 *
8 * ArmarX is distributed in the hope that it will be useful, but
9 * WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 * GNU General Public License for more details.
12 *
13 * You should have received a copy of the GNU General Public License
14 * along with this program. If not, see <http://www.gnu.org/licenses/>.
15 *
16 * @package RobotAPI::RobotUnit
17 * @author Raphael Grimm ( raphael dot grimm at kit dot edu )
18 * @date 2017
19 * @copyright http://www.gnu.org/licenses/gpl-2.0.txt
20 * GNU General Public License
21 */
22#pragma once
23
24#include <algorithm>
25#include <cmath>
26
27namespace armarx
28{
29 template <class FType>
31 {
32 public:
33 using FloatingType = FType;
34
35 PDController(FloatingType p = 0, FloatingType d = 0) : Kp{p}, Kd{d}
36 {
37 }
38
39 // setters / getters
40 /// @see Kp
41 void setP(FloatingType p);
42 /// @see Kp
43 FloatingType getP() const;
44
45 /// @see Kd
46 void setD(FloatingType d);
47 /// @see Kd
48 FloatingType getD() const;
49
50 /**
51 * @brief set limits for the output value
52 * (lo and hi limits are set to the same value)
53 * @see limitOutHi
54 * @see limitOutLo
55 */
56 void limitOut(FloatingType out);
57 /**
58 * @brief set limits for the output value
59 * @see limitOutHi
60 * @see limitOutLo
61 */
63 /// @see limitOutLo
65 /// @see limitOutHi
67
68 /// @see outRampDelta
69 void setOutRampDelta(FloatingType delta);
70 /// @see outRampDelta
72
73 /// @see maxError
74 void setMaxError(FloatingType error);
75 /// @see maxError
77
78 /// @see targetRadius
79 void setTargetRadius(FloatingType radius);
80 /// @see targetRadius
82
83 /// @see lastOutInterpolation
84 void setLastOutInterpolation(FloatingType lastOutFactor);
85 /// @see lastOutInterpolation
87
88 //get controller state
89 /// @see lastTarget
91 /// @see lastInValue
93 /// @see lastOut
95 /// @see iterationCount
96 std::uint64_t getIterationCount() const;
97
98 // updating functions
99 /// @brief reset phe controller
100 void reset();
101 /**
102 * @brief update the controller using the last input and target value
103 * @return the output value for this control iteration
104 */
106 /**
107 * @brief update the controller using the last target value
108 * @param inValue the current input value
109 * @return the output value for this control iteration
110 */
112 /**
113 * @brief update the controller
114 * @param inValue the current input value
115 * @param target the controller target
116 * @return the output value for this control iteration
117 */
119
120 private:
121 /// @brief p portion of the controller
122 FloatingType Kp{0};
123 /// @brief d portion of the controller
124 FloatingType Kd{0};
125
126 /// @brief High limit for the output value
127 FloatingType limitOutHi{0};
128 /// @brief Low limit for the output value
129 FloatingType limitOutLo{0};
130
131 /// @brief The target's radius.
132 /// if abs(error) <= targetRadius the error is 0,
133 /// otherwise the errors magnitude is reduced by targetRadius
134 FloatingType targetRadius{0};
135
136 /// @brief The output can change maximally by this magnitude every time
137 FloatingType outRampDelta{0};
138
139 FloatingType lastOutInterpolation{0};
140
141 /// @brief The error is clamped to -maxError, +maxError
142 FloatingType maxError{0};
143
144 //controller state
145 /// @brief the number of control iterations
146 std::uint64_t iterationCount{0};
147 /// @brief the last control target
148 FloatingType lastTarget{0};
149 /// @brief the last control input value
150 FloatingType lastInValue{0};
151 /// @brief the last control output value
152 FloatingType lastOutValue{0};
153 };
154} // namespace armarx
155
156//functions
157namespace armarx
158{
159 // setters / getters
160 template <class FType>
161 inline void
163 {
164 Kp = std::abs(p);
165 }
166
167 template <class FType>
168 inline FType
170 {
171 return Kp;
172 }
173
174 template <class FType>
175 inline void
177 {
178 Kd = std::abs(d);
179 }
180
181 template <class FType>
182 inline FType
184 {
185 return Kd;
186 }
187
188 template <class FType>
189 inline void
191 {
192 limitOut(-out, out);
193 }
194
195 template <class FType>
196 inline void
198 {
199 std::tie(limitOutLo, limitOutHi) = std::minmax(min, max);
200 }
201
202 template <class FType>
203 inline FType
205 {
206 return limitOutLo;
207 }
208
209 template <class FType>
210 inline FType
212 {
213 return limitOutHi;
214 }
215
216 template <class FType>
217 inline void
219 {
220 outRampDelta = delta;
221 }
222
223 template <class FType>
224 inline FType
226 {
227 return outRampDelta;
228 }
229
230 template <class FType>
231 inline void
233 {
234 maxError = std::abs(error);
235 }
236
237 template <class FType>
238 inline FType
240 {
241 return maxError;
242 }
243
244 template <class FType>
245 inline void
247 {
248 targetRadius = std::abs(radius);
249 }
250
251 template <class FType>
252 inline FType
254 {
255 return targetRadius;
256 }
257
258 template <class FType>
259 inline void
261 {
262 if (!(0 >= lastOutFactor && lastOutFactor < 1))
263 {
264 throw std::invalid_argument{"the interpolation factor has to be in [0, 1)! factor = " +
265 to_string(lastOutFactor)};
266 }
267 lastOutInterpolation = lastOutFactor;
268 }
269
270 template <class FType>
271 inline FType
273 {
274 return lastOutInterpolation;
275 }
276
277 //get controller state
278 template <class FType>
279 inline FType
281 {
282 return lastTarget;
283 }
284
285 template <class FType>
286 inline FType
288 {
289 return lastInValue;
290 }
291
292 template <class FType>
293 inline FType
295 {
296 return lastOutValue;
297 }
298
299 template <class FType>
300 inline uint64_t
302 {
303 return iterationCount;
304 }
305
306 // updating functions
307 template <class FType>
308 inline void
310 {
311 iterationCount = 0;
312 }
313
314 template <class FType>
315 inline FType
317 {
318 return update(lastInValue, lastTarget);
319 }
320
321 template <class FType>
322 inline FType
324 {
325 return update(inValue, lastTarget);
326 }
327
328 template <class FType>
329 inline FType
330 PDController<FType>::update(FType inValue, FType target)
331 {
332 lastTarget = target;
333
334 //calculate error
335 FloatingType error = (target - inValue);
336 if (std::abs(error) < targetRadius)
337 {
338 error = 0;
339 }
340 else
341 {
342 error = sign(error) * (std::abs(error) - targetRadius);
343 }
344 if (maxError != 0)
345 {
346 error = std::clamp(error, -maxError, +maxError);
347 }
348
349 const FloatingType pOut = Kp * error;
350
351 if (!iterationCount)
352 {
353 lastInValue = inValue;
354 lastOutValue = pOut;
355 }
356 ++iterationCount;
357 const FloatingType dOut = -Kd * (inValue - lastInValue);
358 lastInValue = inValue;
359
360 FloatingType out = pOut + dOut;
361
362 if (outRampDelta != 0)
363 {
364 out = std::clamp(out, lastOutValue - outRampDelta, lastOutValue + outRampDelta);
365 }
366 if (limitOutLo != limitOutHi)
367 {
368 out = std::clamp(out, limitOutLo, limitOutHi);
369 }
370 if (lastOutInterpolation != 0)
371 {
372 out = lastOutValue * lastOutInterpolation + out * (1 - lastOutInterpolation);
373 }
374
375 lastOutValue = out;
376 return out;
377 }
378} // namespace armarx
PDController(FloatingType p=0, FloatingType d=0)
FloatingType getMaxError() const
FloatingType getHiOutLimit() const
std::uint64_t getIterationCount() const
void setP(FloatingType p)
FloatingType getP() const
FloatingType getLoOutLimit() const
FloatingType getTargetRadius() const
void setLastOutInterpolation(FloatingType lastOutFactor)
FloatingType getOutRampDelta() const
void limitOut(FloatingType out)
set limits for the output value (lo and hi limits are set to the same value)
FloatingType getD() const
FloatingType getLastInValue() const
FloatingType getLastOutValue() const
void setMaxError(FloatingType error)
void setTargetRadius(FloatingType radius)
FloatingType getLastTarget() const
void setOutRampDelta(FloatingType delta)
void reset()
reset phe controller
void setD(FloatingType d)
FloatingType getLastOutInterpolationFactor() const
FloatingType update()
update the controller using the last input and target value
This file offers overloads of toIce() and fromIce() functions for STL container types.
std::vector< T > max(const std::vector< T > &v1, const std::vector< T > &v2)
T sign(T t)
Definition algorithm.h:214
const std::string & to_string(const std::string &s)
std::vector< T > min(const std::vector< T > &v1, const std::vector< T > &v2)