1. void PID_test() //使用于寻迹小车,
    2. //根据灰度传感器返回值,判断小车是否歪斜,进而调整速度使小车摆正,但是四个麦轮控制速度协调太难了
    3. //调整速度的正负号需要再仔细看一下
    4. {int PID_LEVEL_1=7, //根据转弯幅度设置的三个值
    5. PID_LEVEL_2=8,
    6. PID_LEVEL_3=10;
    7. //定义了三个PID的模式
    8. //PID直线前进循迹
    9. int count=0; //防止第二次调用时速度过快
    10. float error=0;
    11. static float lasterror=0;
    12. float kp=100;//决定每次调节幅度的大小,数值越大调节幅度越大
    13. float ki=0.0f;
    14. float kd=10; //可以决定调节速度的快慢,数值越大调节速度越快,当以比例为主的时候. 可以起到修正作用
    15. float derivative=0; //导数
    16. static float iout=0;
    17. float pid=0;
    18. if(Condition!=-1)
    19. {
    20. Call();
    21. switch(Condition)
    22. {
    23. //-----------------------------直行-------------------------------//
    24. case 0:
    25. //0 1 2 3 4 5//直行
    26. int a;
    27. a=((Glevel[0]<<5)(GLevel[1] << 4) | (GLevel[2] << 3) | (GLevel[3] << 2) | (GLevel[4]<<1) | (GLevel[5]));
    28. switch(a) //这里的灰度全反了,检测到黑线是1,白色是0
    29. {
    30. // case 0x35://左小偏 只有2能检测到 //110111
    31. error=-PID_LEVEL_2;
    32. break;
    33. case 0x3B://右小偏 只有3能检测到 //111011
    34. error=PID_LEVEL_2;
    35. break;
    36. case 0x33://直行不偏转 //110011
    37. error=0;
    38. break;
    39. case 0x39://左中偏 3,4能够检测到 //111001
    40. error=PID_LEVEL_2+1;
    41. break;
    42. case 0x27://右中偏 1 2能够检测到 //100111
    43. error=-PID_LEVEL_2;
    44. break;
    45. case 0x3C://左大偏 右侧灰度检测到 4,5能够检测到 //111100
    46. error=PID_LEVEL_3+1;
    47. break;
    48. case 0x0F://右大偏 0,1 能够检测到 //001111
    49. error=-PID_LEVEL_3+1;
    50. break;
    51. default:
    52. error=0;
    53. break;
    54. }//switch(a)
    55. //------------------------------------后退-----------------------------//
    56. case 1://后退
    57. {
    58. //灰度传感器损坏暂时不写
    59. }
    60. //--------------------------------------左横行---------------------------//
    61. case 2://左横行
    62. //12~16为左,17~21为右,左右两边小数在前,大数在后
    63. //12,13,14,15,16
    64. if(GLevel[14]==1)//当中间的传感器没有检测到黑线的时候
    65. {
    66. count=1000;
    67. LEFT=100;
    68. RIGHT=100;
    69. }
    70. else if(count>0&&GLevel[14]==0)//当中间的两个传感器检测到黑线的时候,
    71. {
    72. count--;
    73. delay_ms(1);
    74. LEFT=pwm_left/8;//这里的LEft需要改---------------------------------------------------
    75. RIGHT=pwm_right/8;//这里的RIGHT需要改--------------------------------------------------
    76. }
    77. int a;
    78. a=((GLevel[12] << 3) | (GLevel[13] << 2) | (GLevel[15] << 1) | (GLevel[16]));
    79. switch(a)
    80. {
    81. case 0x08: //1000
    82. error=PID_LEVEL_2;
    83. break;
    84. case 0x01: //0001
    85. error=-PID_LEVEL_2;
    86. break;
    87. case 0x00: // 0000
    88. error=0;
    89. break;
    90. case 0x06: // 0110
    91. error=0;
    92. break;
    93. case 0x09: // 1001
    94. error=0;
    95. break;
    96. case 0x0D: // 1101
    97. error=PID_LEVEL_1+1;
    98. break;
    99. case 0x0C: // 1100
    100. error=PID_LEVEL_2+1;
    101. break;
    102. case 0x0E: // 1110
    103. error=PID_LEVEL_3+1;
    104. break;
    105. case 0x0B: //1011
    106. error=-PID_LEVEL_1;
    107. break;
    108. case 0x03: // 0011
    109. error=-PID_LEVEL_2;
    110. break;
    111. case 0x07: // 0111
    112. error=-PID_LEVEL_3;
    113. break;
    114. default:
    115. error=0;
    116. break;
    117. }
    118. case 3://右横行
    119. {
    120. if(GLevel[19]==1)//当中间的传感器没有检测到黑线的时候
    121. {
    122. count=1000;
    123. LEFT=100;
    124. RIGHT=100;
    125. }
    126. if(count>0&&GLevel[19]==0)//当中间的两个传感器检测到黑线的时候,
    127. {
    128. count--;
    129. delay_ms(1);
    130. LEFT=pwm_left/8;//这里的LEft需要改---------------------------------------------------
    131. RIGHT=pwm_right/8;//这里的RIGHT需要改--------------------------------------------------
    132. }
    133. //12~16为左,17~21为右,左右两边小数在前,大数在后
    134. //17,18,19,20,21
    135. int a;
    136. a=((GLevel[17] << 3) | (GLevel[18] << 2) | (GLevel[19] << 1) | (GLevel[20]));
    137. switch(a)
    138. {
    139. case 0x08: //1000
    140. error=PID_LEVEL_2;
    141. break;
    142. case 0x01: //0001
    143. error=-PID_LEVEL_2;
    144. break;
    145. case 0x00: // 0000
    146. error=0;
    147. break;
    148. case 0x06: // 0110
    149. error=0;
    150. break;
    151. case 0x09: // 1001
    152. error=0;
    153. break;
    154. case 0x0D: // 1101
    155. error=PID_LEVEL_1+1;
    156. break;
    157. case 0x0C: // 1100
    158. error=PID_LEVEL_2+1;
    159. break;
    160. case 0x0E: // 1110
    161. error=PID_LEVEL_3+1;
    162. break;
    163. case 0x0B: //1011
    164. error=-PID_LEVEL_1;
    165. break;
    166. case 0x03: // 0011
    167. error=-PID_LEVEL_2;
    168. break;
    169. case 0x07: // 0111
    170. error=-PID_LEVEL_3;
    171. break;
    172. default:
    173. error=0;
    174. break;
    175. }
    176. }
    177. }//switch(Condition)
    178. }
    179. //float LEFT=pwm_left;
    180. //float RIGHT=pwm_right;
    181. lasterror=error;
    182. //示例:如果直行左中偏(车在黑线的左侧),error就是正值,左侧加正值,右侧减正值
    183. iout += ki *error;
    184. derivative=error-lasterror;
    185. pid=kp*error+kd*derivative+ki*iout;
    186. pid=pid/10;
    187. // Chassis_Control((LEFT+pid),(RIGHT-pid));
    188. }