44 if (phi.rows() != M * 3)
ThrowNamed(
"Wrong size of Phi!");
46 Eigen::VectorXd eff_Phi;
47 for (
int i = 0; i < M; ++i)
50 eff_Phi(i * 3 + 1) =
kinematics[0].Phi(i).p[1];
51 eff_Phi(i * 3 + 2) =
kinematics[0].Phi(i).p[2];
63 if (phi.rows() != M * 3)
ThrowNamed(
"Wrong size of Phi!");
64 if (jacobian.rows() != M * 3 || jacobian.cols() != N)
ThrowNamed(
"Wrong size of jacobian! " << N);
68 Eigen::VectorXd eff_Phi(M * 3);
69 for (
int i = 0; i < M; ++i)
72 eff_Phi(i * 3 + 1) =
kinematics[0].Phi(i).p[1];
73 eff_Phi(i * 3 + 2) =
kinematics[0].Phi(i).p[2];
77 double A, _A, Sk, Sl,
w, _w;
79 Eigen::Vector3d
distance, _distance = Eigen::Vector3d::Zero(3, 1);
80 for (i = 0; i < N; ++i)
82 for (j = 0; j < M; ++j)
85 jacobian.block(3 * j, i, 3, 1) =
kinematics[0].jacobian[j].data.block(0, i, 3, 1);
86 for (l = 0; l < M; ++l)
90 if (dist(j, l) > 0 && wsum(j) > 0 &&
weights_(j, l) > 0)
92 A = dist(j, l) * wsum(j);
96 distance = eff_Phi.segment(j * 3, 3) - eff_Phi.segment(l * 3, 3);
97 _distance =
kinematics[0].jacobian[j].data.block(0, i, 3, 1) -
kinematics[0].jacobian[l].data.block(0, i, 3, 1);
99 Sl = distance.dot(_distance) / dist(j, l);
100 for (k = 0; k < M; ++k)
102 if (j != k && dist(j, k) > 0 &&
weights_(j, k) > 0)
104 distance = eff_Phi.segment(j * 3, 3) - eff_Phi.segment(k * 3, 3);
105 _distance =
kinematics[0].jacobian[j].data.block(0, i, 3, 1) -
kinematics[0].jacobian[k].data.block(0, i, 3, 1);
106 Sk = distance.dot(_distance) / dist(j, k);
107 _A +=
weights_(j, k) * (Sl * dist(j, k) - Sk * dist(j, l)) / (dist(j, k) * dist(j, k));
110 _w = -
weights_(j, l) * _A / (A * A);
117 jacobian.block(3 * j, i, 3, 1) -= eff_Phi.segment(l * 3, 3) * _w +
kinematics[0].jacobian[l].data.block(0, i, 3, 1) * w;
135 imesh_mark_pub_ = Server::Advertise<visualization_msgs::Marker>(
ns_ +
"/InteractionMesh", 1,
true);
149 weights_.array() = init.Weights.array();
162 static int textid = 0;
166 imesh_mark_.type = visualization_msgs::Marker::LINE_LIST;
170 std::vector<geometry_msgs::Point> points(
eff_size_);
195 std::vector<geometry_msgs::Point> points(
eff_size_);
198 points[i].x = phi(i * 3);
199 points[i].y = phi(i * 3 + 1);
200 points[i].z = phi(i * 3 + 2);
220 imesh_mark_.type = visualization_msgs::Marker::TEXT_VIEW_FACING;
228 textid = (textid + 1) % eff_size_;
235 imesh_mark_.action = visualization_msgs::Marker::DELETE;
247 int N = eff_Phi.rows() / 3;
248 Eigen::VectorXd Phi = Eigen::VectorXd::Zero(N * 3);
249 Eigen::MatrixXd dist = Eigen::MatrixXd::Zero(N, N);
250 Eigen::VectorXd wsum = Eigen::VectorXd::Zero(N);
252 for (
int j = 0; j < N; ++j)
254 for (
int l = j + 1; l < N; ++l)
256 if (!(j >= N && l >= N))
258 dist(j, l) = dist(l, j) = (eff_Phi.segment(j * 3, 3) - eff_Phi.segment(l * 3, 3)).norm();
263 for (
int j = 0; j < N; ++j)
265 for (
int l = 0; l < N; ++l)
267 if (dist(j, l) > 0 && j != l)
269 wsum(j) += weights(j, l) / dist(j, l);
274 for (
int j = 0; j < N; ++j)
276 Phi.segment(j * 3, 3) = eff_Phi.segment(j * 3, 3);
277 for (
int l = 0; l < N; ++l)
281 if (dist(j, l) > 0 && wsum(j) > 0)
283 Phi.segment(j * 3, 3) -= eff_Phi.segment(l * 3, 3) * weights(j, l) / (dist(j, l) * wsum(j));
288 if (dist_ptr) *dist_ptr = dist;
289 if (wsum_ptr) *wsum_ptr = wsum;
295 int N = nodes.size();
296 Eigen::VectorXd eff_Phi(3 * N);
297 for (
int i = 0; i < N; ++i)
299 eff_Phi(i * 3) = nodes[i].p[0];
300 eff_Phi(i * 3 + 1) = nodes[i].p[1];
301 eff_Phi(i * 3 + 2) = nodes[i].p[2];
309 Eigen::VectorXd eff_Phi;
313 eff_Phi(i * 3 + 1) =
kinematics[0].Phi(i).p[1];
314 eff_Phi(i * 3 + 2) =
kinematics[0].Phi(i).p[2];
322 if (i < 0 || i >= M || j < 0 || j >= M)
324 ThrowNamed(
"Invalid weight element (" << i <<
"," << j <<
"). Weight matrix " << M <<
"x" << M);
336 if (weights.rows() != M || weights.cols() != M)
338 ThrowNamed(
"Invalid weight matrix (" << weights.rows() <<
"X" << weights.cols() <<
"). Has to be" << M <<
"x" << M);
std::string GetObjectName()
void Debug(Eigen::VectorXdRefConst phi)
void SetWeight(int i, int j, double weight)
void publish(const boost::shared_ptr< M > &message) const
Eigen::MatrixXd GetWeights()
std::vector< KinematicFrameRequest > frames_
Eigen::Ref< Eigen::VectorXd > VectorXdRef
visualization_msgs::Marker imesh_mark_
std::shared_ptr< Scene > ScenePtr
ros::Publisher imesh_mark_pub_
const Eigen::Ref< const Eigen::MatrixXd > & MatrixXdRefConst
int TaskSpaceDim() override
void Update(Eigen::VectorXdRefConst x, Eigen::VectorXdRef phi) override
void SetWeights(const Eigen::MatrixXd &weights)
const Eigen::Ref< const Eigen::VectorXd > & VectorXdRefConst
void AssignScene(ScenePtr scene) override
void Instantiate(const InteractionMeshInitializer &init) override
TFSIMD_FORCE_INLINE const tfScalar & w() const
Eigen::Ref< Eigen::MatrixXd > MatrixXdRef
void ComputeGoalLaplace(const Eigen::VectorXd &x, Eigen::VectorXd &goal)
static Eigen::VectorXd ComputeLaplace(Eigen::VectorXdRefConst eff_Phi, Eigen::MatrixXdRefConst weights, Eigen::MatrixXd *dist=nullptr, Eigen::VectorXd *wsum=nullptr)
std::string getTopic() const
void InitializeDebug(std::string ref)
virtual ~InteractionMesh()
REGISTER_TASKMAP_TYPE("InteractionMesh", exotica::InteractionMesh)
double distance(const urdf::Pose &transform)