Paths
A path is a pseudo object, representing a succession of points with orientation in space. pseudo object, since it is built using merely dummies and a customization script that describes its functionality and behaviour.
[Simple path containing 4 control points]
Path objects can be added to the scene with [Menu bar --> Add --> Path]. A path is composed by control points that define its curve in space. Control points can be shifted, copy/pasted or deleted. A path's basic properties are accessed and adjusted via its user parameters (implemented via a user config callback function), in the scene hierarchy:
[User parameter icon]
A path can also automatically generate extruded shapes; this functionality is enabled via its user parameters, and the shape profile, color and other details can be adjusted in its customization script, which uses the API function sim.generateShapefromPath:
function path.shaping(path,pathIsClosed,upVector)
-- following section generates a square extrusion shape:
local section={0.02,-0.02,0.02,0.02,-0.02,0.02,-0.02,-0.02,0.02,-0.02}
local color={0.7,0.9,0.9}
local options=0
if pathIsClosed then
options=options|4
end
local shape=sim.generateShapeFromPath(path,section,options,upVector)
sim.setShapeColor(shape,nil,sim.colorcomponent_ambient_diffuse,color)
return shape
end
[Simple path generating an extruded square shape]
To generate an extruded circular shape, use following code to create the section data:
local section={}
local radius=0.02
local sides=32
local da=math.pi*2/sides
for i=0,sides-1,1 do
section[2*i+1]=radius*math.cos(da*i)
section[2*i+2]=radius*math.sin(da*i)
end
-- the section shoujld be closed (first and last points perfect overlap):
section[#section+1]=section[1]
section[#section+1]=section[2]
[Simple path generating an extruded circular shape]
Path data is stored inside of the path object, as custom object data. It can be accessed with:
-- control point data (each one has x,y,z,qx,qy,qz,qw (position and quaternion)):
local ctrlPts=sim.unpackDoubleTable(sim.readCustomDataBlock(pathHandle,'PATHCTRLPTS'))
-- path data (each one has x,y,z,qx,qy,qz,qw (position and quaternion)):
local pathData=sim.unpackDoubleTable(sim.readCustomDataBlock(pathHandle,'PATH')
Various API functions related to paths are available, e.g. in order to have an object follow a path in position and orientation, one could use following script:
function sysCall_init()
objectToFollowPath=sim.getObject('.')
path=sim.getObject('/Path')
pathData=sim.unpackDoubleTable(sim.readCustomDataBlock(path,'PATH'))
local m=Matrix(#pathData//7,7,pathData)
pathPositions=m:slice(1,1,m:rows(),3):data()
pathQuaternions=m:slice(1,4,m:rows(),7):data()
pathLengths,totalLength=sim.getPathLengths(pathPositions,3)
velocity=0.04 -- m/s
posAlongPath=0
previousSimulationTime=0
corout=coroutine.create(coroutineMain)
end
function sysCall_actuation()
if coroutine.status(corout)~='dead' then
local ok,errorMsg=coroutine.resume(corout)
if errorMsg then
error(debug.traceback(corout,errorMsg),2)
end
end
end
function coroutineMain()
sim.setThreadAutomaticSwitch(false)
while true do
local t=sim.getSimulationTime()
posAlongPath=posAlongPath+velocity*(t-previousSimulationTime)
posAlongPath=posAlongPath % totalLength
local pos=sim.getPathInterpolatedConfig(pathPositions,pathLengths,posAlongPath)
local quat=sim.getPathInterpolatedConfig(pathQuaternions,pathLengths,
posAlongPath,nil,{2,2,2,2})
sim.setObjectPosition(objectToFollowPath,path,pos)
sim.setObjectQuaternion(objectToFollowPath,path,quat)
previousSimulationTime=t
sim.switchThread()
end
end
|