Robotis Manipulator  1.0.0
robotis_manipulator_trajectory_generator.cpp
Go to the documentation of this file.
1 /*******************************************************************************
2 * Copyright 2018 ROBOTIS CO., LTD.
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 *******************************************************************************/
16 
17 /* Authors: Darby Lim, Hye-Jong KIM, Ryan Shim, Yong-Ho Na */
18 
26 #include "../../include/robotis_manipulator/robotis_manipulator_trajectory_generator.h"
27 
28 using namespace robotis_manipulator;
29 
31 {
32  coefficient_ = Eigen::VectorXd::Zero(6);
33 }
34 
36 
38  Point goal,
39  double move_time)
40 {
41  Eigen::Matrix3d A = Eigen::Matrix3d::Identity(3, 3);
42  Eigen::Vector3d x = Eigen::Vector3d::Zero();
43  Eigen::Vector3d b = Eigen::Vector3d::Zero();
44 
45  A << pow(move_time, 3), pow(move_time, 4), pow(move_time, 5),
46  3 * pow(move_time, 2), 4 * pow(move_time, 3), 5 * pow(move_time, 4),
47  6 * pow(move_time, 1), 12 * pow(move_time, 2), 20 * pow(move_time, 3);
48 
49  coefficient_(0) = start.position;
50  coefficient_(1) = start.velocity;
51  coefficient_(2) = 0.5 * start.acceleration;
52 
53  b << (goal.position - start.position - (start.velocity * move_time + 0.5 * start.acceleration * pow(move_time, 2))),
54  (goal.velocity - start.velocity - (start.acceleration * move_time)),
55  (goal.acceleration - start.acceleration);
56 
57  Eigen::ColPivHouseholderQR<Eigen::Matrix3d> dec(A);
58  x = dec.solve(b);
59 
60  coefficient_(3) = x(0);
61  coefficient_(4) = x(1);
62  coefficient_(5) = x(2);
63 }
64 
65 Eigen::VectorXd MinimumJerk::getCoefficient()
66 {
67  return coefficient_;
68 }
69 
70 //-------------------- Joint trajectory --------------------//
71 
73 {}
74 
76 
78  JointWaypoint goal)
79 {
80  coefficient_size_ = start.size();
81  minimum_jerk_coefficient_.resize(6,coefficient_size_);
82  for (uint8_t index = 0; index < coefficient_size_; index++)
83  {
84  minimum_jerk_trajectory_generator_.calcCoefficient(start.at(index),
85  goal.at(index),
86  move_time);
87 
88  minimum_jerk_coefficient_.col(index) = minimum_jerk_trajectory_generator_.getCoefficient();
89  }
90 }
91 
93 {
94  JointWaypoint joint_way_point;
95  for (uint8_t index = 0; index < coefficient_size_; index++)
96  {
97  JointValue single_joint_way_point;
98 
99  single_joint_way_point.position = minimum_jerk_coefficient_(0, index) +
100  minimum_jerk_coefficient_(1, index) * pow(tick, 1) +
101  minimum_jerk_coefficient_(2, index) * pow(tick, 2) +
102  minimum_jerk_coefficient_(3, index) * pow(tick, 3) +
103  minimum_jerk_coefficient_(4, index) * pow(tick, 4) +
104  minimum_jerk_coefficient_(5, index) * pow(tick, 5);
105 
106  single_joint_way_point.velocity = minimum_jerk_coefficient_(1, index) +
107  2 * minimum_jerk_coefficient_(2, index) * pow(tick, 1) +
108  3 * minimum_jerk_coefficient_(3, index) * pow(tick, 2) +
109  4 * minimum_jerk_coefficient_(4, index) * pow(tick, 3) +
110  5 * minimum_jerk_coefficient_(5, index) * pow(tick, 4);
111 
112  single_joint_way_point.acceleration = 2 * minimum_jerk_coefficient_(2, index) +
113  6 * minimum_jerk_coefficient_(3, index) * pow(tick, 1) +
114  12 * minimum_jerk_coefficient_(4, index) * pow(tick, 2) +
115  20 * minimum_jerk_coefficient_(5, index) * pow(tick, 3);
116 
117  single_joint_way_point.effort = 0.0;
118 
119  joint_way_point.push_back(single_joint_way_point);
120  }
121 
122  return joint_way_point;
123 }
124 
126 {
127  return minimum_jerk_coefficient_;
128 }
129 
130 //-------------------- Task trajectory --------------------//
131 
133 {
134  minimum_jerk_coefficient_ = Eigen::MatrixXd::Identity(6, 4);
135 }
137 
139  TaskWaypoint goal)
140 {
141  std::vector<Point> start_way_point;
142  std::vector<Point> goal_way_point;
143 
145  for(uint8_t i = 0; i < 3; i++) //x, y, z
146  {
147  Point position_temp;
148  position_temp.position = start.kinematic.position[i];
149  position_temp.velocity = start.dynamic.linear.velocity[i];
150  position_temp.acceleration = start.dynamic.linear.acceleration[i];
151  position_temp.effort = 0.0;
152  start_way_point.push_back(position_temp);
153 
154  position_temp.position = goal.kinematic.position[i];
155  position_temp.velocity = goal.dynamic.linear.velocity[i];
156  position_temp.acceleration = goal.dynamic.linear.acceleration[i];
157  position_temp.effort = 0.0;
158  goal_way_point.push_back(position_temp);
159  }
161 
163 
164  Eigen::Vector3d start_orientation_rpy;
165  Eigen::Vector3d start_ang_vel_rpy;
166  Eigen::Vector3d start_ang_acc_rpy;
167 
168  start_orientation_rpy = math::convertRotationMatrixToRPYVector(start.kinematic.orientation);
169  start_ang_vel_rpy = math::convertOmegaToRPYVelocity(start_orientation_rpy, start.dynamic.angular.velocity);
170  start_ang_acc_rpy = math::convertOmegaDotToRPYAcceleration(start_orientation_rpy, start_ang_vel_rpy, start.dynamic.angular.acceleration);
171 
172  Eigen::Vector3d goal_orientation_rpy;
173  Eigen::Vector3d goal_ang_vel_rpy;
174  Eigen::Vector3d goal_ang_acc_rpy;
175 
176  goal_orientation_rpy = math::convertRotationMatrixToRPYVector(goal.kinematic.orientation);
177  goal_ang_vel_rpy = math::convertOmegaToRPYVelocity(goal_orientation_rpy, goal.dynamic.angular.velocity);
178  start_ang_acc_rpy = math::convertOmegaDotToRPYAcceleration(goal_orientation_rpy, goal_ang_vel_rpy, goal.dynamic.angular.acceleration);
179 
180  for(uint8_t i = 0; i < 3; i++) //roll, pitch, yaw
181  {
182  Point orientation_temp;
183  orientation_temp.position = start_orientation_rpy[i];
184  orientation_temp.velocity = start_ang_vel_rpy[i];
185  orientation_temp.acceleration = start_ang_acc_rpy[i];
186  orientation_temp.effort = 0.0;
187  start_way_point.push_back(orientation_temp);
188 
189  orientation_temp.position = goal_orientation_rpy[i];
190  orientation_temp.velocity = goal_ang_vel_rpy[i];
191  orientation_temp.acceleration = goal_ang_acc_rpy[i];
192  orientation_temp.effort = 0.0;
193  goal_way_point.push_back(orientation_temp);
194  }
196 
197  coefficient_size_ = start_way_point.size();
198  minimum_jerk_coefficient_.resize(6,coefficient_size_);
199  for (uint8_t index = 0; index < coefficient_size_; index++)
200  {
201  minimum_jerk_trajectory_generator_.calcCoefficient(start_way_point.at(index),
202  goal_way_point.at(index),
203  move_time);
204 
205  minimum_jerk_coefficient_.col(index) = minimum_jerk_trajectory_generator_.getCoefficient();
206  }
207 }
208 
210 {
211  std::vector<Point> result_point;
212  for (uint8_t index = 0; index < coefficient_size_; index++)
213  {
214  Point single_task_way_point;
215 
216  single_task_way_point.position = minimum_jerk_coefficient_(0, index) +
217  minimum_jerk_coefficient_(1, index) * pow(tick, 1) +
218  minimum_jerk_coefficient_(2, index) * pow(tick, 2) +
219  minimum_jerk_coefficient_(3, index) * pow(tick, 3) +
220  minimum_jerk_coefficient_(4, index) * pow(tick, 4) +
221  minimum_jerk_coefficient_(5, index) * pow(tick, 5);
222 
223  single_task_way_point.velocity = minimum_jerk_coefficient_(1, index) +
224  2 * minimum_jerk_coefficient_(2, index) * pow(tick, 1) +
225  3 * minimum_jerk_coefficient_(3, index) * pow(tick, 2) +
226  4 * minimum_jerk_coefficient_(4, index) * pow(tick, 3) +
227  5 * minimum_jerk_coefficient_(5, index) * pow(tick, 4);
228 
229  single_task_way_point.acceleration = 2 * minimum_jerk_coefficient_(2, index) +
230  6 * minimum_jerk_coefficient_(3, index) * pow(tick, 1) +
231  12 * minimum_jerk_coefficient_(4, index) * pow(tick, 2) +
232  20 * minimum_jerk_coefficient_(5, index) * pow(tick, 3);
233 
234  single_task_way_point.effort = 0.0;
235 
236  result_point.push_back(single_task_way_point);
237  }
238 
239  TaskWaypoint task_way_point;
241  for(uint8_t i = 0; i < 3; i++) //x ,y ,z
242  {
243  task_way_point.kinematic.position[i] = result_point.at(i).position;
244  task_way_point.dynamic.linear.velocity[i] = result_point.at(i).velocity;
245  task_way_point.dynamic.linear.acceleration[i] = result_point.at(i).acceleration;
246  }
248 
250  Eigen::Vector3d rpy_orientation;
251  rpy_orientation << result_point.at(3).position, result_point.at(4).position, result_point.at(5).position;
252  task_way_point.kinematic.orientation = math::convertRPYToRotationMatrix(result_point.at(3).position, //roll
253  result_point.at(4).position, //pitch
254  result_point.at(5).position); //yaw
255 
256  Eigen::Vector3d rpy_velocity;
257  rpy_velocity << result_point.at(3).velocity, result_point.at(4).velocity, result_point.at(5).velocity;
258  task_way_point.dynamic.angular.velocity = math::convertRPYVelocityToOmega(rpy_orientation, rpy_velocity);
259 
260  Eigen::Vector3d rpy_acceleration;
261  rpy_acceleration << result_point.at(3).acceleration, result_point.at(4).acceleration, result_point.at(5).acceleration;
262  task_way_point.dynamic.angular.acceleration = math::convertRPYAccelerationToOmegaDot(rpy_orientation, rpy_velocity, rpy_acceleration);
263 
264  return task_way_point;
265 }
266 
268 {
269  return minimum_jerk_coefficient_;
270 }
271 
272 
273 /*****************************************************************************
274 ** Trajectory Class
275 *****************************************************************************/
276 void Trajectory::setMoveTime(double move_time)
277 {
278  trajectory_time_.total_move_time = move_time;
279 }
280 
281 void Trajectory::setPresentTime(double present_time)
282 {
283  trajectory_time_.present_time = present_time;
284 }
285 
287 {
288  trajectory_time_.start_time = trajectory_time_.present_time;
289 }
290 
291 void Trajectory::setStartTime(double start_time)
292 {
293  trajectory_time_.start_time = start_time;
294 }
295 
297 {
298  return trajectory_time_.total_move_time;
299 }
300 
302 {
303  return trajectory_time_.present_time - trajectory_time_.start_time;
304 }
305 
307 {
308  manipulator_= manipulator;
309 }
310 
312 {
313  return &manipulator_;
314 }
315 
317 {
318  return joint_;
319 }
320 
322 {
323  return task_;
324 }
325 
327 {
328  return cus_joint_.at(name);
329 }
330 
332 {
333  return cus_task_.at(name);
334 }
335 
336 void Trajectory::addCustomTrajectory(Name trajectory_name, CustomJointTrajectory *custom_trajectory)
337 {
338  cus_joint_.insert(std::make_pair(trajectory_name, custom_trajectory));
339 }
340 
341 void Trajectory::addCustomTrajectory(Name trajectory_name, CustomTaskTrajectory *custom_trajectory)
342 {
343  cus_task_.insert(std::make_pair(trajectory_name, custom_trajectory));
344 }
345 
346 void Trajectory::setCustomTrajectoryOption(Name trajectory_name, const void* arg)
347 {
348  if(cus_joint_.find(trajectory_name) != cus_joint_.end())
349  cus_joint_.at(trajectory_name)->setOption(arg);
350  else if(cus_task_.find(trajectory_name) != cus_task_.end())
351  cus_task_.at(trajectory_name)->setOption(arg);
352 }
353 
354 void Trajectory::setPresentControlToolName(Name present_control_tool_name)
355 {
356  present_control_tool_name_ = present_control_tool_name;
357 }
358 
360 {
361  return present_custom_trajectory_name_;
362 }
363 
365 {
366  return present_control_tool_name_;
367 }
368 
369 void Trajectory::initTrajectoryWaypoint(Manipulator actual_manipulator, Kinematics *kinematics)
370 {
371  setManipulator(actual_manipulator);
372  JointWaypoint joint_way_point_vector;
373  joint_way_point_vector = getManipulator()->getAllActiveJointValue();
374 
375  setPresentJointWaypoint(joint_way_point_vector);
376  updatePresentWaypoint(kinematics);
377 }
378 
380 {
381  //kinematics
382  kinematics->solveForwardKinematics(&manipulator_);
383 }
384 
386 {
387  manipulator_.setAllActiveJointValue(joint_value_vector);
388 }
389 
390 void Trajectory::setPresentTaskWaypoint(Name tool_name, TaskWaypoint tool_value_vector)
391 {
392  manipulator_.setComponentPoseFromWorld(tool_name, tool_value_vector);
393 }
394 
396 {
397  return manipulator_.getAllActiveJointValue();
398 }
399 
401 {
402  return manipulator_.getComponentPoseFromWorld(tool_name);
403 }
404 
406 {
407  for(uint32_t index =0; index < value.size(); index++)
408  {
409  value.at(index).velocity = 0.0;
410  value.at(index).acceleration = 0.0;
411  value.at(index).effort = 0.0;
412  }
413  return value;
414 }
415 
417 {
418  value.dynamic.linear.velocity = Eigen::Vector3d::Zero(3);
419  value.dynamic.linear.acceleration = Eigen::Vector3d::Zero(3);
420  value.dynamic.angular.velocity = Eigen::Vector3d::Zero(3);
421  value.dynamic.angular.acceleration = Eigen::Vector3d::Zero(3);
422  return value;
423 }
424 
425 
426 //Trajectory
428 {
429  trajectory_type_ = trajectory_type;
430 }
431 
433 {
434  if(trajectory_type_==trajectory_type)
435  return true;
436  else
437  return false;
438 }
439 
440 void Trajectory::makeJointTrajectory(JointWaypoint start_way_point, JointWaypoint goal_way_point)
441 {
442  joint_.makeJointTrajectory(trajectory_time_.total_move_time, start_way_point, goal_way_point);
443 }
444 
445 void Trajectory::makeTaskTrajectory(TaskWaypoint start_way_point, TaskWaypoint goal_way_point)
446 {
447  task_.makeTaskTrajectory(trajectory_time_.total_move_time, start_way_point, goal_way_point);
448 }
449 
450 void Trajectory::makeCustomTrajectory(Name trajectory_name, JointWaypoint start_way_point, const void *arg)
451 {
452  if(cus_joint_.find(trajectory_name) != cus_joint_.end())
453  {
454  present_custom_trajectory_name_ = trajectory_name;
455  cus_joint_.at(trajectory_name)->makeJointTrajectory(trajectory_time_.total_move_time, start_way_point, arg);
456  }
457  else
458  log::error("[makeCustomTrajectory] Wrong way point type.");
459 }
460 
461 void Trajectory::makeCustomTrajectory(Name trajectory_name, TaskWaypoint start_way_point, const void *arg)
462 {
463  if(cus_task_.find(trajectory_name) != cus_task_.end())
464  {
465  present_custom_trajectory_name_ = trajectory_name;
466  cus_task_.at(trajectory_name)->makeTaskTrajectory(trajectory_time_.total_move_time, start_way_point, arg);
467  }
468  else
469  log::error("[makeCustomTrajectory] Wrong way point type.");
470 }
471 
472 //tool
473 void Trajectory::setToolGoalPosition(Name tool_name, double tool_goal_position)
474 {
475  manipulator_.setJointPosition(tool_name, tool_goal_position);
476 }
477 
478 
479 void Trajectory::setToolGoalValue(Name tool_name, JointValue tool_goal_value)
480 {
481  manipulator_.setJointValue(tool_name, tool_goal_value);
482 }
483 
485 {
486  return manipulator_.getJointPosition(tool_name);
487 }
488 
490 {
491  return manipulator_.getJointValue(tool_name);
492 }
void setPresentTaskWaypoint(Name tool_name, TaskWaypoint tool_position_value_vector)
setPresentTaskWaypoint
CustomTaskTrajectory * getCustomTaskTrajectory(Name name)
getCustomTaskTrajectory
void setPresentControlToolName(Name present_control_tool_name)
setPresentControlToolName
void addCustomTrajectory(Name trajectory_name, CustomJointTrajectory *custom_trajectory)
addCustomTrajectory
TaskWaypoint getPresentTaskWaypoint(Name tool_name)
getPresentTaskWaypoint
void makeCustomTrajectory(Name trajectory_name, JointWaypoint start_way_point, const void *arg)
makeCustomTrajectory
void calcCoefficient(Point start, Point goal, double move_time)
calcCoefficient
void setCustomTrajectoryOption(Name trajectory_name, const void *arg)
setCustomTrajectoryOption
main namespace
TaskWaypoint getTaskWaypoint(double tick)
getTaskWaypoint
virtual void solveForwardKinematics(Manipulator *manipulator)=0
solveForwardKinematics
Eigen::Vector3d convertRPYVelocityToOmega(Eigen::Vector3d rpy_vector, Eigen::Vector3d rpy_velocity)
convertRPYVelocityToOmega
void setToolGoalPosition(Name tool_name, double tool_goal_position)
setToolGoalPosition
Eigen::MatrixXd getMinimumJerkCoefficient()
getMinimumJerkCoefficient
void makeTaskTrajectory(double move_time, TaskWaypoint start, TaskWaypoint goal)
makeTaskTrajectory
std::vector< JointValue > JointWaypoint
JointWaypoint getPresentJointWaypoint()
getPresentJointWaypoint
void makeJointTrajectory(double move_time, JointWaypoint start, JointWaypoint goal)
makeJointTrajectory
Eigen::Vector3d convertRPYAccelerationToOmegaDot(Eigen::Vector3d rpy_vector, Eigen::Vector3d rpy_velocity, Eigen::Vector3d rpy_acceleration)
convertRPYAccelerationToOmegaDot
void setPresentJointWaypoint(JointWaypoint joint_value_vector)
setPresentJointWaypoint
void updatePresentWaypoint(Kinematics *kinematics)
updatePresentWaypoint
JointValue getToolGoalValue(Name tool_name)
getToolGoalValue
void setToolGoalValue(Name tool_name, JointValue tool_goal_value)
setToolGoalValue
bool checkTrajectoryType(TrajectoryType trajectory_type)
checkTrajectoryType
JointWaypoint getJointWaypoint(double tick)
getJointWaypoint
Eigen::Vector3d convertOmegaToRPYVelocity(Eigen::Vector3d rpy_vector, Eigen::Vector3d omega)
convertOmegaToRPYVelocity
Eigen::MatrixXd getMinimumJerkCoefficient()
getMinimumJerkCoefficient
double getToolGoalPosition(Name tool_name)
getToolGoalPosition
void initTrajectoryWaypoint(Manipulator actual_manipulator, Kinematics *kinematics)
initTrajectoryWaypoint
JointWaypoint removeWaypointDynamicData(JointWaypoint value)
removeWaypointDynamicData
Eigen::Vector3d convertRotationMatrixToRPYVector(const Eigen::Matrix3d &rotation_matrix)
convertRotationMatrixToRPYVector
JointTrajectory getJointTrajectory()
getJointTrajectory
void setManipulator(Manipulator manipulator)
setManipulator
void makeTaskTrajectory(TaskWaypoint start_way_point, TaskWaypoint goal_way_point)
makeTaskTrajectory
Eigen::Vector3d convertOmegaDotToRPYAcceleration(Eigen::Vector3d rpy_vector, Eigen::Vector3d rpy_velocity, Eigen::Vector3d omega_dot)
convertOmegaDotToRPYAcceleration
Name getPresentCustomTrajectoryName()
getPresentCustomTrajectoryName
void setPresentTime(double present_time)
setPresentTime
void makeJointTrajectory(JointWaypoint start_way_point, JointWaypoint goal_way_point)
makeJointTrajectory
Eigen::Matrix3d convertRPYToRotationMatrix(double roll, double pitch, double yaw)
convertRPYToRotationMatrix
CustomJointTrajectory * getCustomJointTrajectory(Name name)
getCustomJointTrajectory
void setTrajectoryType(TrajectoryType trajectory_type)
setTrajectoryType