Tetrapod Project
hierarchical_optimization_controller.h
Go to the documentation of this file.
1 /*******************************************************************/
2 /* AUTHOR: Paal Arthur S. Thorseth */
3 /* ORGN: Dept of Eng Cybernetics, NTNU Trondheim */
4 /* FILE: hierarchical_optimization_controller.h */
5 /* DATE: May 15, 2021 */
6 /* */
7 /* Copyright (C) 2021 Paal Arthur S. Thorseth, */
8 /* Adrian B. Ghansah */
9 /* */
10 /* This program is free software: you can redistribute it */
11 /* and/or modify it under the terms of the GNU General */
12 /* Public License as published by the Free Software Foundation, */
13 /* either version 3 of the License, or (at your option) any */
14 /* later version. */
15 /* */
16 /* This program is distributed in the hope that it will be useful, */
17 /* but WITHOUT ANY WARRANTY; without even the implied warranty */
18 /* of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. */
19 /* See the GNU General Public License for more details. */
20 /* */
21 /* You should have received a copy of the GNU General Public */
22 /* License along with this program. If not, see */
23 /* <https://www.gnu.org/licenses/>. */
24 /* */
25 /*******************************************************************/
26 
27 #pragma once
28 
29 // C++ Standard Library
30 #include <cmath>
31 #include <thread>
32 
33 // ROS
34 #include "ros/ros.h"
35 #include "ros/callback_queue.h"
36 
37 // ROS messages
38 #include "std_msgs/Int8MultiArray.h"
39 #include "std_msgs/Float64MultiArray.h"
40 #include "sensor_msgs/JointState.h"
41 
42 // ROS Package Libraries
43 #include <kinematics/kinematics.h>
45 #include <math_utils/Core>
46 
47 // Eigen
48 #include <Eigen/Core>
49 
50 // Kindr
51 #include <kindr/Core>
52 
53 // Drake C++ Toolbox
54 #include <drake/common/symbolic.h>
55 #include <drake/solvers/mathematical_program.h>
56 #include <drake/solvers/solve.h>
57 #include <drake/solvers/osqp_solver.h>
58 #include <drake/solvers/equality_constrained_qp_solver.h>
59 #include <drake/solvers/clp_solver.h>
60 #include <drake/solvers/scs_solver.h>
61 #include <drake/solvers/snopt_solver.h>
62 
65 {
67  public: struct Task {
68  bool has_eq_constraint = false;
69  bool has_ineq_constraint = false;
70  Eigen::MatrixXd A_eq;
71  Eigen::VectorXd b_eq;
72  Eigen::MatrixXd A_ineq;
73  Eigen::VectorXd b_ineq;
74  };
75 
77  public: enum SolverType { OSQP = 1, ECQP = 2, CLP = 3, SCS = 4, SNOPT = 5, UNSPECIFIED};
78 
80  public: enum LegType { frontLeft = 1, frontRight = 2, rearLeft = 3, rearRight = 4, NONE };
81 
83  public: enum BodyType { base = 1, hip = 2, thigh = 3, leg = 4, foot = 5 };
84 
87 
89  public: virtual ~HierarchicalOptimizationControl();
90 
91  // TODO Remove
92  public: void StaticTorqueTest();
93 
94  // TODO Remove
95  public: void HeightRollYawTest();
96 
116  public: Eigen::Matrix<double, 12, 1> HierarchicalOptimization(const Eigen::Matrix<double, 3, 1> &_desired_base_pos,
117  const Eigen::Matrix<double, 3, 1> &_desired_base_vel,
118  const Eigen::Matrix<double, 3, 1> &_desired_base_acc,
119  const Eigen::Matrix<double, 3, 1> &_desired_base_ori,
120  const Eigen::Matrix<Eigen::Vector3d, 4, 1> &_desired_f_pos,
121  const Eigen::Matrix<Eigen::Vector3d, 4, 1> &_desired_f_vel,
122  const Eigen::Matrix<Eigen::Vector3d, 4, 1> &_desired_f_acc,
123  const Eigen::Matrix<Eigen::Vector3d, 4, 1> &_f_pos,
124  const Eigen::Matrix<Eigen::Vector3d, 4, 1> &_f_vel,
125  const Eigen::Matrix<double, 18, 1> &_q,
126  const Eigen::Matrix<double, 18, 1> &_u,
127  const int &_v = 0);
128 
144  public: Eigen::Matrix<double, Eigen::Dynamic, 1> HierarchicalQPOptimization(const int &_state_dim,
145  const std::vector<Task> &_tasks,
146  const SolverType &_solver = SolverType::OSQP,
147  const int &_v = 0);
148 
164  public: Eigen::Matrix<double, Eigen::Dynamic, 1> HierarchicalLeastSquareOptimization(const Eigen::Matrix<Eigen::MatrixXd, Eigen::Dynamic, 1> &_A,
165  const Eigen::Matrix<Eigen::Matrix<double, Eigen::Dynamic, 1>, Eigen::Dynamic, 1> &_b,
166  const int &_v = 0);
167 
188  public: bool SolveQP(const Eigen::MatrixXd &_Q,
189  const Eigen::VectorXd &_c,
190  const Eigen::MatrixXd &_E_ineq,
191  const Eigen::VectorXd &_f_ineq,
192  Eigen::VectorXd &_sol,
193  const SolverType &_solver = SolverType::UNSPECIFIED,
194  const int &_v = 0);
195 
217  public: bool SolveQP(const Eigen::MatrixXd &_Q,
218  const Eigen::VectorXd &_c,
219  const Eigen::MatrixXd &_A,
220  const Eigen::VectorXd &_lb,
221  const Eigen::VectorXd &_ub,
222  Eigen::VectorXd &_sol,
223  const SolverType &_solver = SolverType::UNSPECIFIED,
224  const int &_v = 0);
225 
249  public: bool SolveQP(const Eigen::MatrixXd &_Q,
250  const Eigen::VectorXd &_c,
251  const Eigen::MatrixXd &_E_eq,
252  const Eigen::VectorXd &_f_eq,
253  const Eigen::MatrixXd &_E_ineq,
254  const Eigen::VectorXd &_f_ineq,
255  Eigen::VectorXd &_sol,
256  const SolverType &_solver = SolverType::UNSPECIFIED,
257  const int &_v = 0);
258 
263  public: void PublishTorqueMsg(const Eigen::Matrix<double, 12, 1> &_desired_tau);
264 
269  public: void OnGenCoordMsg(const std_msgs::Float64MultiArrayConstPtr &_msg);
270 
275  public: void OnGenVelMsg(const std_msgs::Float64MultiArrayConstPtr &_msg);
276 
280  public: void OnContactStateMsg(const std_msgs::Int8MultiArrayConstPtr &_msg);
281 
284  public: void ProcessQueueThread();
285 
288  public: void PublishQueueThread();
289 
291  protected: void InitRos();
292 
295  protected: void InitRosQueueThreads();
296 
298  // TODO Make private
300 
302  private: Eigen::Matrix<double, 18, 1> genCoord;
303 
305  private: Eigen::Matrix<double, 18, 1> genVel;
306 
308  private: Eigen::Matrix<Eigen::Vector3d, 4, 1> fPos;
309 
311  private: Eigen::Matrix<Eigen::Vector3d, 4, 1> fVel;
312 
314  private: int contactState[4];
315 
317  private: std::unique_ptr<ros::NodeHandle> rosNode;
318 
320  private: ros::Subscriber genCoordSub;
321 
323  private: ros::Subscriber genVelSub;
324 
326  private: ros::Subscriber contactStateSub;
327 
329  private: ros::Publisher jointStatePub;
330 
331  // TODO remove as it is only needed to log to plots
333  private: ros::Publisher basePoseCmdPub;
334 
335  // TODO remove as it is only needed to log to plots
337  private: ros::Publisher baseTwistCmdPub;
338 
340  private: ros::CallbackQueue rosProcessQueue;
341 
343  private: ros::CallbackQueue rosPublishQueue;
344 
346  private: std::thread rosProcessQueueThread;
347 
349  private: std::thread rosPublishQueueThread;
350 };
A class for hierarchical optimization control.
ros::Subscriber genVelSub
ROS Generalized Coordinates Subscriber.
std::thread rosProcessQueueThread
Thread running the rosProcessQueue.
std::unique_ptr< ros::NodeHandle > rosNode
Node used for ROS transport.
std::thread rosPublishQueueThread
Thread running the rosPublishQueue.
Eigen::Matrix< double, 18, 1 > genCoord
Generalized Coordinates.
bool SolveQP(const Eigen::MatrixXd &_Q, const Eigen::VectorXd &_c, const Eigen::MatrixXd &_E_ineq, const Eigen::VectorXd &_f_ineq, Eigen::VectorXd &_sol, const SolverType &_solver=SolverType::UNSPECIFIED, const int &_v=0)
The SolveQP function solves a (convex) quadratic program (QP) on the form:
void PublishTorqueMsg(const Eigen::Matrix< double, 12, 1 > &_desired_tau)
The PublishTorqueMsg function publishes a desired torque message to the ROS topic set by the joint st...
Eigen::Matrix< double, Eigen::Dynamic, 1 > HierarchicalQPOptimization(const int &_state_dim, const std::vector< Task > &_tasks, const SolverType &_solver=SolverType::OSQP, const int &_v=0)
The HierarchicalQPOptimization function finds the optimal solution for a set of tasks in a strictly p...
ros::CallbackQueue rosProcessQueue
ROS callbackque that helps process messages.
Eigen::Matrix< double, 18, 1 > genVel
Generalized Velocities.
void ProcessQueueThread()
The ProcessQueueThread function is a ROS helper function that processes messages.
void OnGenCoordMsg(const std_msgs::Float64MultiArrayConstPtr &_msg)
The OnGenCoordMsg function handles an incoming generalized coordinates message from ROS.
Eigen::Matrix< Eigen::Vector3d, 4, 1 > fVel
Foot-point velocities.
void InitRosQueueThreads()
The InitRosQueueThreads function is called to initialize the ROS Publish and Process Queue Threads.
Eigen::Matrix< double, 12, 1 > HierarchicalOptimization(const Eigen::Matrix< double, 3, 1 > &_desired_base_pos, const Eigen::Matrix< double, 3, 1 > &_desired_base_vel, const Eigen::Matrix< double, 3, 1 > &_desired_base_acc, const Eigen::Matrix< double, 3, 1 > &_desired_base_ori, const Eigen::Matrix< Eigen::Vector3d, 4, 1 > &_desired_f_pos, const Eigen::Matrix< Eigen::Vector3d, 4, 1 > &_desired_f_vel, const Eigen::Matrix< Eigen::Vector3d, 4, 1 > &_desired_f_acc, const Eigen::Matrix< Eigen::Vector3d, 4, 1 > &_f_pos, const Eigen::Matrix< Eigen::Vector3d, 4, 1 > &_f_vel, const Eigen::Matrix< double, 18, 1 > &_q, const Eigen::Matrix< double, 18, 1 > &_u, const int &_v=0)
The HierarchicalOptimization function finds the optimal joint torques for a desired motion plan....
void OnContactStateMsg(const std_msgs::Int8MultiArrayConstPtr &_msg)
The OnContactStateMsg function handles an incoming contact state message from ROS.
Eigen::Matrix< Eigen::Vector3d, 4, 1 > fPos
Foot-point positions.
void PublishQueueThread()
The PublishQueueThread function is a ROS helper function that publish state messages.
ros::Publisher jointStatePub
ROS Joint State Publisher.
Eigen::Matrix< double, Eigen::Dynamic, 1 > HierarchicalLeastSquareOptimization(const Eigen::Matrix< Eigen::MatrixXd, Eigen::Dynamic, 1 > &_A, const Eigen::Matrix< Eigen::Matrix< double, Eigen::Dynamic, 1 >, Eigen::Dynamic, 1 > &_b, const int &_v=0)
The HierarchicalLeastSquareOptimization function finds the optimal solution for a set of linear equal...
void InitRos()
The InitRos function is called to initialize ROS.
void OnGenVelMsg(const std_msgs::Float64MultiArrayConstPtr &_msg)
The OnGenVelMsg function handles an incoming generalized velocities message from ROS.
ros::Subscriber genCoordSub
ROS Generalized Coordinates Subscriber.
ros::CallbackQueue rosPublishQueue
ROS callbackque that helps publish messages.
ros::Publisher basePoseCmdPub
ROS Base Position Command Publisher.
ros::Subscriber contactStateSub
ROS Contact State Subscriber.
ros::Publisher baseTwistCmdPub
ROS Base Position Command Publisher.
A class for analytical Kinematics Solving.
Definition: kinematics.h:54
bool has_eq_constraint
Bool indicating whether the task has a linear equality constraint.
Eigen::MatrixXd A_ineq
Linear inequality constraint matrix A.
Eigen::VectorXd b_ineq
Linear inequality constraint vector b.
Eigen::VectorXd b_eq
Linear equality constraint vector b.
bool has_ineq_constraint
Bool indicating whether the task has a linear inequality constraint.
Eigen::MatrixXd A_eq
Linear equality constraint matrix A.