Advertisement
Guest User

AutoTuneMightWork

a guest
Feb 26th, 2017
83
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Java 4.80 KB | None | 0 0
  1. #include <PID_v1.h>
  2. #include <PID_AutoTune_v0.h>
  3. #include <QTRSensors.h>
  4.  
  5. #define NUM_SENSORS             5
  6. #define NUM_SAMPLES_PER_SENSOR  2
  7. #define EMITTER_PIN             QTR_NO_EMITTER_PIN  
  8.  
  9. #define inA 2
  10. #define inB 4
  11. #define inC 6
  12. #define inD 7
  13. #define enA 3
  14. #define enB 5
  15.  
  16. QTRSensorsAnalog qtra((unsigned char[]) {0, 1, 2, 3, 4}, NUM_SENSORS, NUM_SAMPLES_PER_SENSOR, EMITTER_PIN);
  17. unsigned int sensorValues[NUM_SENSORS];
  18.  
  19. int baseSpeed = 150;
  20. int maxSpeed = 250;
  21.  
  22. byte ATuneModeRemember=2;
  23. double input=80, output=50, setpoint=180;
  24. double kp=0.2,ki=0.5,kd=2.25;
  25.  
  26. double kpmodel=1.5, taup=100, theta[50];
  27. double outputStart=5;
  28. double aTuneStep=50, aTuneNoise=1, aTuneStartValue=100;
  29. unsigned int aTuneLookBack=20;
  30.  
  31. boolean tuning = true;
  32. unsigned long  modelTime, serialTime;
  33.  
  34. PID myPID(&input, &output, &setpoint,kp,ki,kd, DIRECT);
  35. PID_ATune aTune(&input, &output);
  36.  
  37. //set to false to connect to the real world
  38. boolean useSimulation = false;
  39.  
  40. void setup()
  41. {
  42.   initializePins();
  43.   calibrateSensors();
  44.  
  45.   if(useSimulation)
  46.   {
  47.     for(byte i=0;i<50;i++)
  48.     {
  49.       theta[i]=outputStart;
  50.     }
  51.     modelTime = 0;
  52.   }
  53.   //Setup the pid
  54.   myPID.SetMode(AUTOMATIC);
  55.  
  56.   if(tuning)
  57.   {
  58.     tuning=false;
  59.     changeAutoTune();
  60.     tuning=true;
  61.   }
  62.  
  63.   serialTime = 0;
  64.   Serial.begin(9600);
  65. }
  66.  
  67. void loop()
  68. {
  69.   unsigned long now = millis();
  70.  
  71.   if(!useSimulation)
  72.   { //pull the input in from the real world
  73.     input = (int)qtra.readLine(sensorValues, QTR_EMITTERS_ON, true);
  74.   }
  75.  
  76.   if(tuning)
  77.   {
  78.     byte val = (aTune.Runtime());
  79.     if (val!=0)
  80.     {
  81.       tuning = false;
  82.     }
  83.     if(!tuning)
  84.     { //we're done, set the tuning parameters
  85.       kp = aTune.GetKp();
  86.       ki = aTune.GetKi();
  87.       kd = aTune.GetKd();
  88.       myPID.SetTunings(kp,ki,kd);
  89.       AutoTuneHelper(false);
  90.     }
  91.   }
  92.   else myPID.Compute();
  93.  
  94.   if(useSimulation)
  95.   {
  96.     theta[30]=output;
  97.     if(now>=modelTime)
  98.     {
  99.       modelTime +=100;
  100.       DoModel();
  101.     }
  102.   }
  103.   else
  104.   {
  105.      analogWrite(0,output);
  106.   }
  107.  
  108.   //send-receive with processing if it's time
  109.   if(millis()>serialTime)
  110.   {
  111.     SerialReceive();
  112.     SerialSend();
  113.     serialTime+=500;
  114.   }
  115.  
  116.   wheel(baseSpeed + (int)(round(output)), baseSpeed - (int)(round(output)));
  117. }
  118.  
  119. void changeAutoTune()
  120. {
  121.  if(!tuning)
  122.   {
  123.     //Set the output to the desired starting frequency.
  124.     output=aTuneStartValue;
  125.     aTune.SetNoiseBand(aTuneNoise);
  126.     aTune.SetOutputStep(aTuneStep);
  127.     aTune.SetLookbackSec((int)aTuneLookBack);
  128.     AutoTuneHelper(true);
  129.     tuning = true;
  130.   }
  131.   else
  132.   { //cancel autotune
  133.     aTune.Cancel();
  134.     tuning = false;
  135.     AutoTuneHelper(false);
  136.   }
  137. }
  138.  
  139. void AutoTuneHelper(boolean start)
  140. {
  141.   if(start)
  142.     ATuneModeRemember = myPID.GetMode();
  143.   else
  144.     myPID.SetMode(ATuneModeRemember);
  145. }
  146.  
  147.  
  148. void SerialSend()
  149. {
  150.   Serial.print("setpoint: ");Serial.print(setpoint); Serial.print(" ");
  151.   Serial.print("input: ");Serial.print(input); Serial.print(" ");
  152.   Serial.print("output: ");Serial.print(output); Serial.print(" ");
  153.   if(tuning){
  154.     Serial.println("tuning mode");
  155.   } else {
  156.     Serial.print("kp: ");Serial.print(myPID.GetKp());Serial.print(" ");
  157.     Serial.print("ki: ");Serial.print(myPID.GetKi());Serial.print(" ");
  158.     Serial.print("kd: ");Serial.print(myPID.GetKd());Serial.println();
  159.   }
  160. }
  161.  
  162. void SerialReceive()
  163. {
  164.   if(Serial.available())
  165.   {
  166.    char b = Serial.read();
  167.    Serial.flush();
  168.    if((b=='1' && !tuning) || (b!='1' && tuning))changeAutoTune();
  169.   }
  170. }
  171.  
  172. void DoModel()
  173. {
  174.   //cycle the dead time
  175.   for(byte i=0;i<49;i++)
  176.   {
  177.     theta[i] = theta[i+1];
  178.   }
  179.   //compute the input
  180.   input = (kpmodel / taup) *(theta[0]-outputStart) + input*(1-1/taup) + ((float)random(-10,10))/100;
  181. }
  182.  
  183. void initializePins()
  184. {
  185.   pinMode(inA, OUTPUT);
  186.   pinMode(inB, OUTPUT);
  187.   pinMode(inC, OUTPUT);
  188.   pinMode(inD, OUTPUT);
  189.   pinMode(enA, OUTPUT);
  190.   pinMode(enB, OUTPUT);
  191.  
  192.   digitalWrite(inA, HIGH);
  193.   digitalWrite(inB, HIGH);
  194.   digitalWrite(inC, HIGH);
  195.   digitalWrite(inD, HIGH);
  196.  
  197.   digitalWrite(enA, LOW);
  198.   digitalWrite(enB, LOW);
  199. }
  200.  
  201. void wheel(int lm, int rm)
  202. {
  203.   if(lm>maxSpeed) lm=maxSpeed;
  204.   if(lm<-maxSpeed) lm=-maxSpeed;
  205.   if(rm>maxSpeed) rm=maxSpeed;
  206.   if(rm<-maxSpeed) rm=-maxSpeed;
  207.  
  208.   analogWrite(enA,abs(rm));
  209.   analogWrite(enB,abs(lm));
  210.  
  211.   if(lm==0)
  212.   {
  213.     digitalWrite(inC,HIGH);
  214.     digitalWrite(inD,HIGH);
  215.   }
  216.   if(lm<0)
  217.   {
  218.     digitalWrite(inC,HIGH);
  219.     digitalWrite(inD,LOW);
  220.   }
  221.   else if(lm>0)
  222.   {
  223.     digitalWrite(inC,LOW);
  224.     digitalWrite(inD,HIGH);
  225.   }
  226.  
  227.  
  228.   if(rm==0)
  229.   {
  230.     digitalWrite(inA,HIGH);
  231.     digitalWrite(inB,HIGH);
  232.   }
  233.   if(rm<0)
  234.   {
  235.     digitalWrite(inA,HIGH);
  236.     digitalWrite(inB,LOW);
  237.   }
  238.   else if(rm>0)
  239.   {
  240.     digitalWrite(inA,LOW);
  241.     digitalWrite(inB,HIGH);
  242.   }
  243. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement