ROBOTC.net forumshttp://www.robotc.net/forums/ PID Line Following?http://www.robotc.net/forums/viewtopic.php?f=11&t=3988 Page 1 of 1

 Author: contagon [ Sat Jan 07, 2012 7:06 pm ] Post subject: PID Line Following? I've read through the link below and feel I have gotten a fairly good grasp on how a PID controller works. http://www.inpharmix.com/jps/PID_Controller_For_Lego_Mindstorms_Robots.htmlI read on another sight that you could use 2+ sensors (I'm considering 3 or 4) in a PID loop. I was wondering how you would integrate this since the link I read through only uses one? Also I read about "grey level sensors" and was wondering if any would be willing to explain them to me.Thanks, Contagon

Author:  MHTS [ Sat Jan 07, 2012 10:55 pm ]
Post subject:  Re: PID Line Following?

PID controller takes an "input" and compares that "input" with the "target" value to compute the "error". Then it computes the "output" according to the "error" value. So the trick is to translate the multiple light sensor readings to a single "input" value. There are many ways to do that. A simple way is to treat each light sensor as a digital trigger: above threshold or below threshold. Let's say you have 3 light sensors. This will gives you three binary bits. If a light sensor is above threshold, you will get a "1", else you will get a "0". If you translate the 3 light sensor values to 3 binary digits, the most significant bit being the left sensor, the least significant bit being the right sensor and the middle bit being the center sensor, you will have a possibility of 8 values:
 Code:0 0 0    No line detected0 0 1    Line is on the far right side0 1 0    Line is at the center0 1 1    Line is slightly to the right1 0 0    Line is on the far left side1 0 1    Impossible or you have reached a Y junction1 1 0    Line is slightly to the left1 1 1    Impossible or the line is horizontal covering all three sensors

Then you have to decide what action you should map each of these values to.
For example:
 Code:0 0 0 => -999   No line detected0 0 1 => 2    Line is on the far right side, turn right hard0 1 0 => 0    Line is at the center, go straight0 1 1 => 1    Line is slightly to the right, turn right easy1 0 0 =>-2   Line is on the far left side, turn left hard1 0 1 => -888 Impossible or you have reached a Y junction1 1 0 => -1   Line is slightly to the left, turn left easy1 1 1 => -777  Impossible or the line is horizontal covering all three sensors

Don't know what you want to do with the special cases of -777, -888 and -999 but for the other cases, you use the mapped values (-2, -1, 0, 1, 2) as the error to your PID controller for calculating the output. So 0 will make the robot stay straight ahead, 1 will turn slightly to the right, 2 will turn harder to the right, -1 will turn slightly to the left and -2 will turn harder to the left.
Does it make sense?

 Author: contagon [ Sun Jan 08, 2012 6:46 pm ] Post subject: Re: PID Line Following? Yes, that makes a lot of sense, thanks. A few more questions though, if you wouldn't mind. Isn't that a relatively small range? Would the only way to increase this range be adding more sensors?Also, I assumed that you would line them up right next to each other, but would it work better to put them more in a V pattern or somewhere along those lines?

Author:  MHTS [ Mon Jan 09, 2012 2:19 am ]
Post subject:  Re: PID Line Following?

 contagon wrote:Isn't that a relatively small range? Would the only way to increase this range be adding more sensors?

Increasing the number of sensors usually will allow the robot to go higher speed when going into curves. This is because more sensors usually means wider width so if the robot "overshoots", wider sensor array means one of the sensors at the ends of the array still sees the line. If you have a narrow sensor array, you could very easily "lose the line" on turns. But if you have higher sensor density (i.e. more sensors but not too much increase in width, you have higher resolution), it means you will track the line more accurately. But if you overshoot on a turn, you can still lose the line. If you are talking about the range of the numbers (from -2 to +2), that's irrelevant since in PID you are going to multiply with Kp anyway so you could end up with -50 to 50 (if multiply by 25). Regarding sensor resolution, there are tricks to make 3 analog light sensors to become 7 virtual digital light sensors by interpolation. This trick will give you higher sensor resolution but it won't increase the overall sensor width. Adding more discrete light sensors on the NXT is problematic because of the limited number of sensor ports (even with sensor MUX, the ports go fast). If you are serious about tracking the line better, you may consider a single sensor that is actually a light sensor array (http://www.mindsensors.com/index.php?mo ... AGE_id=111).
 contagon wrote:Also, I assumed that you would line them up right next to each other, but would it work better to put them more in a V pattern or somewhere along those lines?

Regarding the V-shape sensor arrangement, in my opinion, it doesn't really offer too much advantage over moving a straight line sensor array more forward on the robot. Both will give you "time" to react to the "change". V shape may complicate the algorithm like the bit-map one I mentioned. For example, one arm of the V may totally light up when the robot turns at a certain angle. It's hard to interpret what to do in such a scenario.

Author:  magicode [ Mon Jan 09, 2012 11:41 am ]
Post subject:  Re: PID Line Following?

I would like to put up one point in favor of the v formation. If you're doing sharp 90 degree turns when you hit a line and want to be parallel to that line, the V formation will make that a lot easier. Many VEX teams do this with 2 line followers in the front of the robot, and one in the center.
 Code:_____0____________0________|                         ||                         | |           0             ||                         |where 0 = line follower

 Author: contagon [ Mon Jan 09, 2012 8:30 pm ] Post subject: Re: PID Line Following? Alright, I was talking about the -2 to 2 range. I'm using vex, and it's just a straight line so I believe I should be fine with a PID loop, 3 sensors and that range. My problem with the range was that that only gives me 5 different possibilities with the proportional part of the PID, but I should still be fine with the ID part. I'll post a code in a little while asking if it should work. Is there any other tips on using/making a PID controller that you could help me with?

 Author: MHTS [ Mon Jan 09, 2012 8:44 pm ] Post subject: Re: PID Line Following? If the number of possibilities is what you are worrying about, that's the resolution I was talking about. You only get 5 possibilities out of 3 light sensors. Like I said, there is a trick to interpolate the 3 light sensors into 7 light sensors. That will give you about 13 possibilities. But that requires more precise calibration of each individual light sensors.

Author:  contagon [ Tue Jan 10, 2012 12:52 am ]
Post subject:  Re: PID Line Following?

Alright, I follow you now. So this is rather simple, but would something along these lines work?
 Code:#pragma config(Sensor, in1,    le,                  sensorReflection)#pragma config(Sensor, in2,    middle,              sensorReflection)#pragma config(Sensor, in3,    ri,                  sensorReflection)#pragma config(Motor,  port1,           rimotor,       tmotorNormal, openLoop)#pragma config(Motor,  port2,           leftmotor,     tmotorNormal, openLoop)//*!!Code automatically generated by 'ROBOTC' configuration wizard               !!*//task main{float kp = 0;float ki = 0;float kd = 0;float offset = (SensorValue[le] + SensorValue[ri]) / 2;int finderror = 0;float turn = 0;float error = 0;float toppower = 87;float integral = 0;float derivative = 0;float lasterror = 0;int max = 0;int min = 0;while(1 == 1){  finderror = SensorValue[le] < offset ? error + 100 : error;  finderror = SensorValue[middle] < offset ? error + 10 : error;  finderror = SensorValue[ri] < offset ? error + 1 : error;  switch(finderror){    case 100:    error = -2;    break;    case 110:    error = -1;    break;    case 010:    error = 0;    break;    case 011:    error = 1;    break;    case 001:    error = 2;    break;  }  integral = integral + error;  derivative = error - lasterlasterror;  turn = (kp * error) + (ki * error) + (kd * error);  turn = turn > max ? max : turn;  turn = turn < min ? min : turn;  motor[rimotor] = toppower + turn;  motor[lemotor] = toppower - turn;  lasterror = error;  }}

Also would it be worth looking into the interpolation for something this simply? And if it is, would you mind pointing me somewhere or explaining? And thanks for all your help again, you've been a great help!

Author:  MHTS [ Tue Jan 10, 2012 1:20 am ]
Post subject:  Re: PID Line Following?

I think it's even simpler than that.
 Code:#define ERR_NO_LINE    -999#define ERR_Y          -888#define ERR_T          -777const int errorMap[8] = {        /*0 0 0*/ ERR_NO_LINE,        /*0 0 1*/ 2,        /*0 1 0*/ 0,        /*0 1 1*/ 1,        /*1 0 0*/ -2,        /*1 0 1*/ ERR_Y,        /*1 1 0*/ -1,        /*1 1 1*/ ERR_T};while (1 == 1){    int index = SensorValue[le] < threshold? 4: 0 +                SensorValue[middle] < threshold? 2: 0 +                SensorValue[ri] < threshold? 1: 0;    int error = errorMap[index];    if (error == ERR_NO_LINE)    {        // We lost the line, what to do? Stop?    }    else if (error == ERR_Y)    {        // We came to a Y, what to do?    }    else if (error == ERR_T)    {        // We came to a T, what to do?    }    else    {        // do your PID control here.    }}etcetc

 Page 1 of 1 All times are UTC - 5 hours [ DST ] Powered by phpBB © 2000, 2002, 2005, 2007 phpBB Grouphttp://www.phpbb.com/