Beginners: please read this post and this post before posting to the forum.

0 Members and 1 Guest are viewing this topic.

/* * A generic PID controller based on pseudo code from Wikipedia: * http://en.wikipedia.org/wiki/PID_controller * previous_error = 0 integral = 0 start: error = setpoint - actual_position integral = integral + (error*dt) derivative = (error - previous_error)/dt output = (Kp*error) + (Ki*integral) + (Kd*derivative) previous_error = error wait(dt) goto start * */#ifndef PID_H_#define PID_H_typedef struct s_pid { float kP; // proportional scale factor float kI; // integral scale factor float kD; // derivative scale factor float integral; // The sum of the integral component float setPoint; // The desired output position float prevError; // The previous error amount TICK_COUNT lastTime; // The last time I was called by setActual} PID;// Update the PID with the desired target position - the setPointvoid pidSetTarget(PID* pid,float setPoint);// Update the PID with the actual position and return the new outputfloat pidSetActual(PID* pid,float actual);// Construct a new PID controller#define MAKE_PID(kP,kI,kD) {kP,kI,kD,(float)(0.0),(float)(0.0),(float(0.0),(TICK_COUNT)0}#endif /* PID_H_ */

my heading PD (I skipped the I, usually it's more hassle tuning the system gains with an I then it's worth)

Good point, I always skip the I too. I recommend also adding a PD only option.

you'll all beat me up with practical problems and documentation issues

I'll take a crack at it

MCU loading gauge

typedef struct s_pid { float kP; // proportional scale factor float kI; // integral scale factor float kD; // derivative scale factor float inMax; //input maximum float inMin; //input min float inSpan; //the span of input, calculated by pre-processor macro to avoid work for MCU float outMax; //max PID output float outMin; //min PID output float Ilimit; //limit to avoid wind-up boolean isCircular; //is this a circular system, like a compass or cont rotation actuator? float integral; // The sum of the integral component float setPoint; // The desired output position float prevError; // The previous error amount TICK_COUNT lastTime; // The last time I was called by setActual} PID;

Webbot, we couldn't ditch floating point numbers altogether as the gains will always have to be floating point, so i don't think there's a benefit to switching the rest.