Skip to content
Snippets Groups Projects
Commit 61130d88 authored by Hawo Höfer's avatar Hawo Höfer
Browse files

make AbstractManipulability::getEllipsoidOrientationAndScale continuous

for better visualization
parent fee3de87
No related branches found
No related tags found
No related merge requests found
...@@ -108,26 +108,71 @@ VisualizationNodePtr AbstractManipulability::getManipulabilityVis(const Eigen::M ...@@ -108,26 +108,71 @@ VisualizationNodePtr AbstractManipulability::getManipulabilityVis(const Eigen::M
return vis; return vis;
} }
void AbstractManipulability::getEllipsoidOrientationAndScale(const Eigen::MatrixXd &manipulability, Eigen::Quaternionf &orientation, Eigen::Vector3d &scale) { void AbstractManipulability::getEllipsoidOrientationAndScale(const Eigen::MatrixXd& manipulability, Eigen::Quaternionf& orientation, Eigen::Vector3d& scale) {
Eigen::MatrixXd reduced_manipulability = (mode != Mode::Orientation || manipulability.rows() == 3) ? manipulability.block(0, 0, 3, 3) : manipulability.block(3, 3, 3, 3); Eigen::Matrix3d reduced_manipulability =
(mode != Mode::Orientation || manipulability.rows() == 3)
? manipulability.block(0, 0, 3, 3)
: manipulability.block(3, 3, 3, 3);
Eigen::SelfAdjointEigenSolver<Eigen::MatrixXd> eigenSolver(reduced_manipulability); Eigen::SelfAdjointEigenSolver<Eigen::MatrixXd> eigenSolver(reduced_manipulability);
Eigen::MatrixXd eigenVectors = eigenSolver.eigenvectors(); const Eigen::Matrix3d& eigenVectors = eigenSolver.eigenvectors();
Eigen::VectorXd eigenValues = eigenSolver.eigenvalues(); const Eigen::Vector3d& eigenValues = eigenSolver.eigenvalues();
Eigen::VectorXd v1 = eigenVectors.col(eigenVectors.cols() - 1);
Eigen::VectorXd v2 = eigenVectors.col(eigenVectors.cols() - 2); // Eigenvectors are the columns of the matrix 'eigenVectors'
// they are already normalized to have length 1
orientation = Eigen::Quaterniond::FromTwoVectors(v1, v2).cast<float>(); // we sort them by the eigenvalues
struct VecVal
// normalize singular values for scaling {
eigenValues /= eigenValues.sum(); Eigen::Vector3d vec;
for (int i = 0; i < eigenValues.rows(); i++) { double val;
if (eigenValues(i) < 0.005) // 5mm };
eigenValues(i) = 0.005; std::array<VecVal, 3> decomp = {
VecVal{.vec = eigenVectors.col(0), .val = eigenValues(0)},
VecVal{.vec = eigenVectors.col(1), .val = eigenValues(1)},
VecVal{.vec = eigenVectors.col(2), .val = eigenValues(2)},
};
std::sort(decomp.begin(),
decomp.end(),
[](const auto& a, const auto& b) { return a.val > b.val; });
Eigen::Matrix3d transform;
transform.col(0) = decomp[0].vec;
transform.col(1) = decomp[1].vec;
transform.col(2) = decomp[2].vec;
// Rectify the transformation matrix representing the orientation of the ellipse
// We need to make sure that is *special* orthogonal, not just orthogonal
// Flip the signs of eigenvectors that point opposite the first quadrant
// Sum of the elements is the same as a dot product with (1, 1, 1)
// We want this so that the directions of the eigenvectors is consistent,
// and because this makes transform have determinant 1
for (int col = 0; col < transform.cols(); ++col)
{
if (transform.col(col).sum() < 0.0)
{
transform.col(col) *= -1.0;
}
}
// if the matrix still has determinant smaller than one, just flip one of the vectors back. This may be the case if all of the columns point opposite (1, 1, 1)
if (transform.determinant() < 0)
{
transform.col(2) *= -1;
}
orientation = transform.cast<float>();
// Normalize eigenvalues for scaling
Eigen::Vector3d s =
Eigen::Vector3d(decomp[0].val, decomp[1].val, decomp[2].val).array().sqrt();
s /= s.sum();
for (int i = 0; i < s.rows(); i++)
{
if (s(i) < 0.005) // 5mm
s(i) = 0.005;
} }
scale(0) = eigenValues(eigenValues.rows() - 1); scale(0) = s(0);
scale(1) = eigenValues(eigenValues.rows() - 2); scale(1) = s(1);
scale(2) = eigenValues(eigenValues.rows() - 3); scale(2) = s(2);
} }
void AbstractManipulability::getEllipsoidOrientationAndScale(Eigen::Quaternionf &orientation, Eigen::Vector3d &scale) { void AbstractManipulability::getEllipsoidOrientationAndScale(Eigen::Quaternionf &orientation, Eigen::Vector3d &scale) {
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment