Pioneer_p3dx 小车路径规划与控制算法实现
function run(P,D)
data2={}
PD=0
error=0
for i=1,5,1 do
res,data=sim.readVisionSensor(floorSensorHandles[i])
if(res>=0)then
data2[i]=data[11]
end
end
if(data2[4]<0.73) then
data2[3]=0
end
if(data2[2]<0.73) then
data2[1]=0
end
if(data2[2]<data2[4]) then
if(data2[3]<data2[1]) then
error=math.abs(data2[5]-0.095)+math.abs(data2[3]-0.85)+math.abs(data2[2]-0.85)
else
error=math.abs(data2[5]-0.095)+math.abs(data2[1]-0.85)+math.abs(data2[2]-0.85)
end
else
if(data2[3]<data2[1]) then
error=math.abs(data2[5]-0.095)+math.abs(data2[3]-0.85)+math.abs(data2[4]-0.85)
else
error=math.abs(data2[5]-0.095)+math.abs(data2[1]-0.85)+math.abs(data2[4]-0.85)
end
end
PD=P*error+D*(error-previousError)
previousError=error
previousdata=data2
if error<0.2 then
rightV=speed
leftV=speed
previousError=0
elseif data2[3]<0.75 or data2[4]<0.75 then
rightV=speed+PD*speed
leftV=speed-PD*speed
elseif data2[1]<0.75 or data2[2]<0.75 then
rightV=speed-PD*speed
leftV=speed+PD*speed
end
sim.setJointTargetVelocity(leftmotor,leftV)
sim.setJointTargetVelocity(rightmotor,rightV)
end
function sysCall_threadmain()
leftmotor=sim.getObjectHandle('Pioneer_p3dx_leftMotor')
rightmotor=sim.getObjectHandle('Pioneer_p3dx_rightMotor')
car=sim.getObjectHandle('P1')
floorSensorHandles={-1,-1,-1,-1,-1}
floorSensorHandles[1]=sim.getObjectHandle('l')
floorSensorHandles[2]=sim.getObjectHandle('m')
floorSensorHandles[3]=sim.getObjectHandle('r')
floorSensorHandles[4]=sim.getObjectHandle('m0')
floorSensorHandles[5]=sim.getObjectHandle('m2')
postion1={-0.09,-1.37}
ccc={-1,-1,-1}
aaa=-1
bbb=-1
speed=-5
back=-1
previousError=0
previousdata={}
flag={0,0,0,0,0,0,0,0}
stop={{-0.1,0.099},{-0.731,0.098},{-1.302,0.104},{-1.469,1.263},{-0.782,1.299},{0.238,1.296},{0.822,1.284},{0.6,0.131}}
sim.setIntegerSignal('occupy2',1)
sim.setJointTargetVelocity(leftmotor,0)
sim.setJointTargetVelocity(rightmotor,0)
sim.setIntegerSignal('arrive2',1)
sim.waitForSignal('finish2')
sim.clearIntegerSignal('finish2')
while true do
if(sim.getIntegerSignal('occupy3')==nil) then
break
end
end
sim.clearIntegerSignal('occupy2')
flag={0,1,0,0,0,0,0,0}
while sim.getSimulationState()~=sim.simulation_advancing_abouttostop do
position=sim.getObjectPosition(car,-1)
if (math.abs(position[1]-stop[1][1])<0.05)and(math.abs(position[2]-stop[1][2])<0.05) and (flag[1]==0) then
sim.setIntegerSignal('occupy1',1)
sim.setJointTargetVelocity(leftmotor,0)
sim.setJointTargetVelocity(rightmotor,0)
sim.wait(0.8)
sim.setIntegerSignal('arrive1',1)
sim.waitForSignal('finish1')
sim.clearIntegerSignal('finish1')
while true do
if(sim.getIntegerSignal('occupy2')==nil) then
break
end
end
sim.clearIntegerSignal('occupy1')
flag={1,0,0,0,0,0,0,0}
end
if (math.abs(position[1]-stop[2][1])<0.05)and(math.abs(position[2]-stop[2][2])<0.05) and (flag[2]==0) then
sim.setIntegerSignal('occupy2',1)
sim.setJointTargetVelocity(leftmotor,0)
sim.setJointTargetVelocity(rightmotor,0)
sim.wait(0.8)
sim.setIntegerSignal('arrive2',1)
sim.waitForSignal('finish2')
sim.clearIntegerSignal('finish2')
while true do
if(sim.getIntegerSignal('occupy3')==nil) then
break
end
end
sim.clearIntegerSignal('occupy2')
flag={0,1,0,0,0,0,0,0}
end
if (math.abs(position[1]-stop[5][1])<0.05)and(math.abs(position[2]-stop[5][2])<0.05) and (flag[5]==0) then
sim.setIntegerSignal('occupy5',1)
sim.setJointTargetVelocity(leftmotor,0)
sim.setJointTargetVelocity(rightmotor,0)
sim.wait(0.8)
sim.setIntegerSignal('arrive5',1)
sim.waitForSignal('finish5')
sim.clearIntegerSignal('finish5')
while true do
if(sim.getIntegerSignal('occupy6')==nil) then
break
end
end
sim.clearIntegerSignal('occupy5')
flag={0,0,0,0,1,0,0,0}
end
if (math.abs(position[1]-stop[6][1])<0.05)and(math.abs(position[2]-stop[6][2])<0.05) and (flag[6]==0) then
sim.setIntegerSignal('occupy6',1)
sim.setJointTargetVelocity(leftmotor,0)
sim.setJointTargetVelocity(rightmotor,0)
sim.wait(0.8)
sim.setIntegerSignal('arrive6',1)
sim.waitForSignal('finish6')
sim.clearIntegerSignal('finish6')
while true do
if(sim.getIntegerSignal('occupy7')==nil) then
break
end
end
sim.clearIntegerSignal('occupy6')
flag={0,0,0,0,0,1,0,0}
end
if (math.abs(position[1]-stop[3][1])<0.05)and(math.abs(position[2]-stop[3][2])<0.05) and (flag[3]==0) then
sim.setIntegerSignal('occupy3',1)
if(sim.getIntegerSignal('occupy4')==nil) then
sim.clearIntegerSignal('occupy3')
else
sim.setJointTargetVelocity(leftmotor,0)
sim.setJointTargetVelocity(rightmotor,0)
while true do
if(sim.getIntegerSignal('occupy4')==nil) then
break
end
end
sim.clearIntegerSignal('occupy3')
end
flag={0,0,1,0,0,0,0,0}
end
if (math.abs(position[1]-stop[4][1])<0.05)and(math.abs(position[2]-stop[4][2])<0.05) and (flag[4]==0) then
sim.setIntegerSignal('occupy4',1)
if(sim.getIntegerSignal('occupy5')==nil) then
sim.clearIntegerSignal('occupy4')
else
sim.setJointTargetVelocity(leftmotor,0)
sim.setJointTargetVelocity(rightmotor,0)
while true do
if(sim.getIntegerSignal('occupy5')==nil) then
break
end
end
sim.clearIntegerSignal('occupy4')
end
flag={0,0,0,1,0,0,0,0}
end
if (math.abs(position[1]-stop[7][1])<0.05)and(math.abs(position[2]-stop[7][2])<0.05) and (flag[7]==0) then
sim.setIntegerSignal('occupy7',1)
if(sim.getIntegerSignal('occupy8')==nil) then
sim.clearIntegerSignal('occupy7')
else
sim.setJointTargetVelocity(leftmotor,0)
sim.setJointTargetVelocity(rightmotor,0)
while true do
if(sim.getIntegerSignal('occupy8')==nil) then
break
end
end
sim.clearIntegerSignal('occupy7')
end
flag={0,0,0,0,0,0,1,0}
end
if (math.abs(position[1]-stop[8][1])<0.05)and(math.abs(position[2]-stop[8][2])<0.05) and (flag[8]==0) then
sim.setIntegerSignal('occupy8',1)
if(sim.getIntegerSignal('occupy1')==nil) then
sim.clearIntegerSignal('occupy8')
else
sim.setJointTargetVelocity(leftmotor,0)
sim.setJointTargetVelocity(rightmotor,0)
while true do
if(sim.getIntegerSignal('occupy1')==nil) then
break
end
end
sim.clearIntegerSignal('occupy8')
end
flag={0,0,0,0,0,0,0,1}
end
run(0.22,0.06)
end
end
逐句分析内容:
- 定义函数
run(P,D),该函数接受两个参数P和D,表示控制器的比例系数和微分系数。 - 初始化变量
data2、PD和error。 - 通过循环读取地面传感器的数据,并将其存储在
data2中。 - 根据传感器数据对
data2进行调整。 - 根据
data2中的数据计算出误差值error。 - 根据误差值和比例系数、微分系数计算出
PD值。 - 根据
error值和一些条件,计算出左右轮的速度。 - 设置左右轮的速度。
- 定义函数
sysCall_threadmain(),该函数为主线程函数。 - 获取左右轮的句柄和小车的句柄。
- 获取地面传感器的句柄。
- 初始化变量
postion1、ccc、aaa、bbb、speed、back、previousError、previousdata和flag。 - 设置停靠点的坐标。
- 设置信号量
occupy2为 1,表示小车已经到达第二个停靠点。 - 停止左右轮的运动。
- 等待信号量
arrive2。 - 清除信号量
finish2。 - 当模拟器未停止时,执行以下操作:
- 获取小车的位置。
- 如果小车到达了第一个停靠点,并且
flag[1]为 0,则设置信号量occupy1为 1,表示小车已经到达第一个停靠点。 - 停止左右轮的运动。
- 等待一段时间。
- 设置信号量
arrive1。 - 等待信号量
finish1。 - 清除信号量
finish1。 - 如果
occupy2信号量不存在,则跳出循环。 - 清除信号量
occupy1。 - 设置
flag中的相应元素为 1,表示小车已经到达了第一个停靠点。 - 如果小车到达了第二个停靠点,并且
flag[2]为 0,则设置信号量occupy2为 1,表示小车已经到达第二个停靠点。 - 停止左右轮的运动。
- 等待一段时间。
- 设置信号量
arrive2。 - 等待信号量
finish2。 - 清除信号量
finish2。 - 如果
occupy3信号量不存在,则跳出循环。 - 清除信号量
occupy2。 - 设置
flag中的相应元素为 1,表示小车已经到达了第二个停靠点。 - 如果小车到达了第五个停靠点,并且
flag[5]为 0,则设置信号量occupy5为 1,表示小车已经到达第五个停靠点。 - 停止左右轮的运动。
- 等待一段时间。
- 设置信号量
arrive5。 - 等待信号量
finish5。 - 清除信号量
finish5。 - 如果
occupy6信号量不存在,则跳出循环。 - 清除信号量
occupy5。 - 设置
flag中的相应元素为 1,表示小车已经到达了第五个停靠点。 - 如果小车到达了第六个停靠点,并且
flag[6]为 0,则设置信号量occupy6为 1,表示小车已经到达第六个停靠点。 - 停止左右轮的运动。
- 等待一段时间。
- 设置信号量
arrive6。 - 等待信号量
finish6。 - 清除信号量
finish6。 - 如果
occupy7信号量不存在,则跳出循环。 - 清除信号量
occupy6。 - 设置
flag中的相应元素为 1,表示小车已经到达了第六个停靠点。 - 如果小车到达了第三个停靠点,并且
flag[3]为 0,则设置信号量occupy3为 1,表示小车已经到达第三个停靠点。 - 如果
occupy4信号量不存在,则清除信号量occupy3。 - 否则,停止左右轮的运动,并等待信号量
occupy4清除。 - 清除信号量
occupy3。 - 设置
flag中的相应元素为 1,表示小车已经到达了第三个停靠点。 - 如果小车到达了第四个停靠点,并且
flag[4]为 0,则设置信号量occupy4为 1,表示小车已经到达第四个停靠点。 - 如果
occupy5信号量不存在,则清除信号量occupy4。 - 否则,停止左右轮的运动,并等待信号量
occupy5清除。 - 清除信号量
occupy4。 - 设置
flag中的相应元素为 1,表示小车已经到达了第四个停靠点。 - 如果小车到达了第七个停靠点,并且
flag[7]为 0,则设置信号量occupy7为 1,表示小车已经到达第七个停靠点。 - 如果
occupy8信号量不存在,则清除信号量occupy7。 - 否则,停止左右轮的运动,并等待信号量
occupy8清除。 - 清除信号量
occupy7。 - 设置
flag中的相应元素为 1,表示小车已经到达了第七个停靠点。 - 如果小车到达了第八个停靠点,并且
flag[8]为 0,则设置信号量occupy8为 1,表示小车已经到达第八个停靠点。 - 如果
occupy1信号量不存在,则清除信号量occupy8。 - 否则,停止左右轮的运动,并等待信号量
occupy1清除
原文地址: https://www.cveoy.top/t/topic/oWf6 著作权归作者所有。请勿转载和采集!