Basic but robust PID library
Dependents: ESP8266_pid_mtrPos_webserver_SDcard_v2 ESP8266_pid_mtrSpeed_Webserver_SDcard ESP8266_pid_spd_and_pos_webserver_SDcard ESP8266_pid_redbot_webserver ... more
Diff: PID.h
- Revision:
- 0:9a6f7aafe531
- Child:
- 2:07397aa513c6
diff -r 000000000000 -r 9a6f7aafe531 PID.h --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/PID.h Mon Nov 23 02:42:53 2015 +0000 @@ -0,0 +1,100 @@ +#ifndef PID_H +#define PID_H +#include "mbed.h" +#include <algorithm> + +/* + Bryce Williams 11/19/2015 + + PID Controller Class based on Brett Beauregard's Arduino PID Library + and PID blog post. + + Brett Beauregard's blog post explains the PID code implementation very well + and discusses why the actual equation is a bit different than the classical + equation, i.e. he explains and implements how to overcome windup, dervative + kick, etc. This class uses the same implementation, but adds interrupt + driven computation. + + Reference Links: + 1. Arduion Library: + (http://playground.arduino.cc/Code/PIDLibrary) + 2. Brett Beauregard's PID Blog: + (http://brettbeauregard.com/blog/2011/04/improving-the-beginners- + pid-introduction/) +*/ + +class PID{ + public: + /* + Constructor for PID objects. + + Note: PID objects use given pointers, ie setpoint, + feedback, output inside interrupts. When reading/ modifying + these vars make sure we don't have possible read/write + conflicts if the interrupt fires. Either ensure reads/writes + are atomic operations, or call the stop() method perform the + read/write and then call the start() method. + */ + PID(float* setpoint, float* feedback, float* output, + float output_lower, float output_upper, + float kp, float ki, float kd, float Ts); + /* + Starts PID Controller; Attaches sample() as callback to Ticker + sample_timer and starts the interrupt + */ + void start(); + /* + Stops PID Contoller; detaches callback from Ticker sample_timer. + Allows manual setting of output. + */ + void stop(); + /* + Increments/ decrements Gain values and Sample time + by the given value. Gives a simple method to + programatically step through different values; just put in a + loop and go + @param delta_"name" The value that will be added to its currently set value + */ +// void adjust_parameters(float delta_kp, float delta_ki, float delta_kd, float delta Ts); + /* + Overwrite Gain and Sample Time parameters with new + values + Note: sample_timer interrupt is disabled during update + to avoid synch issues. + + */ + void set_parameters(float kp, float ki, float kd, float Ts); + + /* + returns current error + */ + float getError(); + + private: + float _kp, _ki, _kd; // PID Gain values + float _Ts; // Sample time is seconds + float* _setpoint; // Pointer to setpoint value + float* _feedback; // Pointer to sensor feedback value (sensor input) + float* _output; // Pointer to control output value + float _output_lower; // Ouput Lower Limit + float _output_upper; // Output Upper Limit + + float i_accumulator; // Integral Term accumulator + float last_feedback; // Previous feedback value + float error; // Feedback error term + Ticker sample_timer; // Generates the sample time interrupt and calls sample() + /* + sample() performs next sample calculationand updates command value + */ + void sample(); + /* + Clips value to lower/ uppper + @param value The value to clip + @param lower The mininum allowable value + @param upper The maximum allowable value + @return The resulting clipped value + */ + float clip(float value, float lower, float upper); +}; + +#endif \ No newline at end of file