Merge branch 'vector-cross-method' into 'master'

VectorT: Implement .cross() and .dot() methods.

See merge request OpenMesh/OpenMesh!256
This commit is contained in:
Jan Möbius
2020-04-20 08:00:10 +02:00
2 changed files with 47 additions and 5 deletions

View File

@@ -369,7 +369,7 @@ class VectorT {
} }
/// cross product: only defined for Vec3* as specialization /// cross product: only defined for Vec3* as specialization
/// \see OpenMesh::cross /// \see OpenMesh::cross and .cross()
template<typename OtherScalar> template<typename OtherScalar>
auto operator% (const VectorT<OtherScalar, DIM> &_rhs) const -> auto operator% (const VectorT<OtherScalar, DIM> &_rhs) const ->
typename std::enable_if<DIM == 3, typename std::enable_if<DIM == 3,
@@ -382,8 +382,18 @@ class VectorT {
}; };
} }
/// cross product: only defined for Vec3* as specialization
/// \see OpenMesh::cross and .operator%
template<typename OtherScalar>
auto cross (const VectorT<OtherScalar, DIM> &_rhs) const ->
decltype(*this % _rhs)
{
return *this % _rhs;
}
/// compute scalar product /// compute scalar product
/// \see OpenMesh::dot /// \see OpenMesh::dot and .dot()
template<typename OtherScalar> template<typename OtherScalar>
auto operator|(const VectorT<OtherScalar, DIM>& _rhs) const -> auto operator|(const VectorT<OtherScalar, DIM>& _rhs) const ->
decltype(*this->data() * *_rhs.data()) { decltype(*this->data() * *_rhs.data()) {
@@ -392,6 +402,15 @@ class VectorT {
*begin() * *_rhs.begin()); *begin() * *_rhs.begin());
} }
/// compute scalar product
/// \see OpenMesh::dot and .operator|
template<typename OtherScalar>
auto dot(const VectorT<OtherScalar, DIM>& _rhs) const ->
decltype(*this | _rhs)
{
return *this | _rhs;
}
//------------------------------------------------------------ euclidean norm //------------------------------------------------------------ euclidean norm
/// \name Euclidean norm calculations /// \name Euclidean norm calculations

View File

@@ -263,6 +263,23 @@ TEST_F(OpenMeshVectorTest, BasicArithmeticImmutable) {
EXPECT_NEAR(-2, v2neg[1], epsilon); EXPECT_NEAR(-2, v2neg[1], epsilon);
EXPECT_NEAR(-3, v2neg[2], epsilon); EXPECT_NEAR(-3, v2neg[2], epsilon);
} }
template <typename V1, typename V2, typename S>
void test_dot(const V1 &v1, const V2 &v2, const S&s) {
EXPECT_NEAR(s, v1 | v2, 1e-6);
EXPECT_NEAR(s, v1.dot(v2), 1e-6);
EXPECT_NEAR(-s, (-v1) | v2, 1e-6);
EXPECT_NEAR(-s, (-v1).dot(v2), 1e-6);
EXPECT_NEAR(s, v2 | v1, 1e-6);
EXPECT_NEAR(s, v2.dot(v1), 1e-6);
}
template <typename V1, typename V2, typename V3>
void test_cross(const V1 &v1, const V2 &v2, const V3 &res) {
EXPECT_NEAR(0, (v1.cross(v2) - res).norm(), 1e-6);
EXPECT_NEAR(0, (v1 % v2 - res).norm(), 1e-6);
EXPECT_NEAR(0, (v2.cross(v1) + res).norm(), 1e-6);
EXPECT_NEAR(0, (v2 % v1 + res).norm(), 1e-6);
}
TEST_F(OpenMeshVectorTest, BasicLinearAlgebra) { TEST_F(OpenMeshVectorTest, BasicLinearAlgebra) {
OpenMesh::Vec3d v(1, 2, 3); OpenMesh::Vec3d v(1, 2, 3);
@@ -285,9 +302,15 @@ TEST_F(OpenMeshVectorTest, BasicLinearAlgebra) {
EXPECT_EQ(1, OpenMesh::Vec3d(1, 3, -4).min_abs()); EXPECT_EQ(1, OpenMesh::Vec3d(1, 3, -4).min_abs());
EXPECT_EQ(2, OpenMesh::Vec3d(-4, 2, 3).min_abs()); EXPECT_EQ(2, OpenMesh::Vec3d(-4, 2, 3).min_abs());
EXPECT_NEAR(14, OpenMesh::Vec3d(1, 2, 3) | OpenMesh::Vec3d(1, 2, 3), 1e-6);
EXPECT_NEAR(-14, OpenMesh::Vec3d(1, 2, 3) | OpenMesh::Vec3d(-1, -2, -3), 1e-6); test_dot(OpenMesh::Vec3d(1, 2, 3), OpenMesh::Vec3d(1, 2, 3), 14.);
EXPECT_NEAR(14, OpenMesh::Vec3d(-1, -2, -3) | OpenMesh::Vec3d(-1, -2, -3), 1e-6); test_dot(OpenMesh::Vec3d(1, 2, 3), OpenMesh::Vec3d(-1, -2, -3), -14.);
test_dot(OpenMesh::Vec3d(1, 2, 3), OpenMesh::Vec3i(1, 2, 3), 14);
test_dot(OpenMesh::Vec3i(1, 2, 3), OpenMesh::Vec3i(1, 2, 3), 14);
test_cross(OpenMesh::Vec3i(2, 0, 0), OpenMesh::Vec3i(0, 3, 0), OpenMesh::Vec3i(0, 0, 6));
test_cross(OpenMesh::Vec3d(2, 0, 0), OpenMesh::Vec3d(0, 3, 0), OpenMesh::Vec3d(0, 0, 6));
test_cross(OpenMesh::Vec3d(2, 0, 0), OpenMesh::Vec3i(0, 3, 0), OpenMesh::Vec3d(0, 0, 6));
} }
TEST_F(OpenMeshVectorTest, array_init) { TEST_F(OpenMeshVectorTest, array_init) {