-
Notifications
You must be signed in to change notification settings - Fork 8
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
GRIDEDIT-758 Added mesh transformation. #247
Merged
lucacarniato
merged 20 commits into
master
from
feature/GRIDEDIT-758_transform_cartesian_grid
Nov 10, 2023
Merged
Changes from 12 commits
Commits
Show all changes
20 commits
Select commit
Hold shift + click to select a range
82b470f
GRIDEDIT-758 Added mesh transformation.
BillSenior cfb4815
GRIDEDIT-758 Updated comments, added check for Cartesian projection
BillSenior a746c77
GRIDEDIT-758 Added missing headers, another try to get windows building
BillSenior c41f8f8
GRIDEDIT-758 Renamed the apply function to operator()
BillSenior 2212ba3
GRIDEDIT-758 One last attempt at getting the windows build working wi…
BillSenior 0eb4484
GRIDEDIT-758 Windows now building with concepts, problem was in incor…
BillSenior 0a64e42
GRIDEDIT-758
BillSenior afd1244
GRIDEDIT-758 Changed loop variable to signed int for openmp
BillSenior 548b943
GRIDEDIT-758 Corrected headers
BillSenior cd1f32f
GRIDEDIT-758 Removed potentially confusing composition function, corr…
BillSenior 1b1ea36
GRIDEDIT-758 Minor update to exception error message
BillSenior 2e8f9da
GRIDEDIT-758 Added a transformation projection function
BillSenior b57a106
Merge branch 'master' into feature/GRIDEDIT-758_transform_cartesian_grid
BillSenior f4ef83b
Add no discard
lucacarniato 36c5df1
GRIDEDIT-758 Changes made after code reivew
BillSenior 4bcbf4a
Merge branch 'feature/GRIDEDIT-758_transform_cartesian_grid' of https…
BillSenior 9f6f689
GRIDEDIT-758 Added call to administrate after node transformation
BillSenior 18e868d
GRIDEDIT-758 Fixed sonarcloud warnings
BillSenior e03370c
GRIDEDIT-758 Removed file added by mistake
BillSenior 5765c47
GRIDEDIT-758 Added mesh kernel api functions for translation and rota…
BillSenior File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
279 changes: 279 additions & 0 deletions
279
libs/MeshKernel/include/MeshKernel/MeshTransformation.hpp
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,279 @@ | ||
//---- GPL --------------------------------------------------------------------- | ||
// | ||
// Copyright (C) Stichting Deltares, 2011-2023. | ||
// | ||
// This program is free software: you can redistribute it and/or modify | ||
// it under the terms of the GNU General Public License as published by | ||
// the Free Software Foundation version 3. | ||
// | ||
// This program is distributed in the hope that it will be useful, | ||
// but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||
// GNU General Public License for more details. | ||
// | ||
// You should have received a copy of the GNU General Public License | ||
// along with this program. If not, see <http://www.gnu.org/licenses/>. | ||
// | ||
// contact: [email protected] | ||
// Stichting Deltares | ||
// P.O. Box 177 | ||
// 2600 MH Delft, The Netherlands | ||
// | ||
// All indications and logos of, and references to, "Delft3D" and "Deltares" | ||
// are registered trademarks of Stichting Deltares, and remain the property of | ||
// Stichting Deltares. All rights reserved. | ||
// | ||
//------------------------------------------------------------------------------ | ||
|
||
#pragma once | ||
|
||
#include <cmath> | ||
#include <concepts> | ||
|
||
#include "MeshKernel/Definitions.hpp" | ||
#include "MeshKernel/Exceptions.hpp" | ||
#include "MeshKernel/Mesh.hpp" | ||
#include "MeshKernel/Point.hpp" | ||
#include "MeshKernel/Vector.hpp" | ||
|
||
namespace meshkernel | ||
{ | ||
|
||
/// @brief Ensure any instantiation of the MeshTransformation Compute function is with the correct operation | ||
template <typename Function> | ||
concept HasTransformationFunction = requires(Function op, Point p) {{ op(p)} -> std::same_as<Point>; }; | ||
|
||
/// @brief Ensure any instantiation of the MeshTransformation Compute function is able to determine the projection. | ||
template <typename Function> | ||
concept HasTransformationProjection = requires(Function op) {{ op.TransformationProjection()} -> std::same_as<Projection>; }; | ||
|
||
/// @brief To ensure the MeshTransformation Compute template parameter has a valid interface. | ||
template <typename Function> | ||
concept TransformationFunction = HasTransformationFunction<Function> && HasTransformationProjection<Function>; | ||
|
||
/// @brief Apply a translation transformation to a point or a vector. | ||
class Translation | ||
{ | ||
public: | ||
/// @brief Default constructor, default is no translation | ||
Translation() = default; | ||
|
||
/// @brief Construct with user defined translation | ||
explicit Translation(const Vector& trans) : translation(trans) {} | ||
|
||
/// @brief Get the projection required for the translation | ||
Projection TransformationProjection() const | ||
{ | ||
return Projection::cartesian; | ||
} | ||
|
||
/// @brief Reset translation to identity translation (i.e. no translation) | ||
void identity() | ||
{ | ||
translation = {0.0, 0.0}; | ||
} | ||
|
||
/// @brief Reset the translation to a new translation quantity | ||
void reset(const Vector& trans) | ||
{ | ||
translation = trans; | ||
} | ||
|
||
/// @brief Get the current defined translation vector. | ||
const Vector& vector() const | ||
{ | ||
return translation; | ||
} | ||
|
||
/// @brief Compose two translation objects. | ||
Translation compose(const Translation& trans) const | ||
{ | ||
return Translation(translation + trans.translation); | ||
} | ||
|
||
/// @brief Apply the translation to a point in Cartesian coordinate system | ||
Point operator()(const Point& pnt) const | ||
{ | ||
return pnt + translation; | ||
} | ||
|
||
/// @brief Apply the translation to a vector in Cartesian coordinate system | ||
Vector operator()(const Vector& vec) const | ||
{ | ||
return vec + translation; | ||
} | ||
|
||
private: | ||
/// @brief The translation values | ||
Vector translation{0.0, 0.0}; | ||
}; | ||
|
||
/// @brief Apply a rotation transformation to a point or a vector. | ||
class Rotation | ||
{ | ||
public: | ||
/// @brief Default constructor, default is theta = 0. | ||
Rotation() = default; | ||
|
||
/// @brief Construct with user defined rotation angle, in radians. | ||
explicit Rotation(const double angle) : theta(angle), cosTheta(std::cos(angle)), sinTheta(std::sin(angle)) {} | ||
|
||
/// @brief Get the projection required for the rotation | ||
Projection TransformationProjection() const | ||
{ | ||
return Projection::cartesian; | ||
} | ||
|
||
/// @brief Reset rotation to identity translation (i.e. no rotation, theta = 0) | ||
void identity() | ||
{ | ||
theta = 0.0; | ||
cosTheta = 1.0; | ||
sinTheta = 0.0; | ||
} | ||
|
||
/// @brief Reset the rotation to a new rotation angle | ||
void reset(const double angle) | ||
{ | ||
theta = angle; | ||
cosTheta = std::cos(theta); | ||
sinTheta = std::sin(theta); | ||
} | ||
|
||
/// @brief Get the current defined rotation angle | ||
double angle() const | ||
{ | ||
return theta; | ||
} | ||
|
||
/// @brief Compose two rotation objects. | ||
Rotation compose(const Rotation& rot) const | ||
{ | ||
return Rotation(theta + rot.theta); | ||
} | ||
|
||
/// @brief Apply the rotation to a point in Cartesian coordinate system | ||
Point operator()(const Point& pnt) const | ||
{ | ||
Point result({cosTheta * pnt.x - sinTheta * pnt.y, sinTheta * pnt.x + cosTheta * pnt.y}); | ||
return result; | ||
} | ||
|
||
/// @brief Apply the rotation to a vector in Cartesian coordinate system | ||
Vector operator()(const Vector& vec) const | ||
{ | ||
Vector result({cosTheta * vec.x() - sinTheta * vec.y(), | ||
sinTheta * vec.x() + cosTheta * vec.y()}); | ||
return result; | ||
} | ||
|
||
private: | ||
/// @brief The rotation angle, theta | ||
double theta = 0.0; | ||
|
||
/// @brief cosine of the rotation angle | ||
double cosTheta = 1.0; | ||
|
||
/// @brief sine of the rotation angle | ||
double sinTheta = 0.0; | ||
}; | ||
|
||
/// @brief A composition of translation and rotation transformations | ||
class RigidBodyTransformation | ||
{ | ||
public: | ||
/// @brief Default constructor, default is no transformation | ||
RigidBodyTransformation() = default; | ||
|
||
/// @brief Get the projection required for the transformation | ||
Projection TransformationProjection() const | ||
{ | ||
return Projection::cartesian; | ||
} | ||
|
||
/// @brief Reset transformation to identity transformation (i.e. no transformation) | ||
void identity() | ||
{ | ||
rotation_.identity(); | ||
translation_.identity(); | ||
} | ||
|
||
/// @brief Compose rotation and transformation object. | ||
/// | ||
/// Will be applied: rot (transformation). | ||
void compose(const Rotation& rot) | ||
{ | ||
rotation_ = rot.compose(rotation_); | ||
translation_.reset(rot(translation_.vector())); | ||
} | ||
|
||
/// @brief Compose translation and transformation object. | ||
/// | ||
/// Will be applied: translation (transformation). | ||
void compose(const Translation& trans) | ||
{ | ||
translation_ = trans.compose(translation_); | ||
} | ||
|
||
/// @brief Get the current rotation. | ||
const Rotation& rotation() const | ||
{ | ||
return rotation_; | ||
} | ||
|
||
/// @brief Get the current translation. | ||
const Translation& translation() const | ||
{ | ||
return translation_; | ||
} | ||
|
||
/// @brief Apply the transformation to a point in Cartesian coordinate system | ||
Point operator()(const Point& pnt) const | ||
{ | ||
Point result = rotation_(pnt); | ||
result = translation_(result); | ||
return result; | ||
} | ||
|
||
/// @brief Apply the transformation to a vector in Cartesian coordinate system | ||
Vector operator()(const Vector& vec) const | ||
{ | ||
Vector result = rotation_(vec); | ||
result = translation_(result); | ||
return result; | ||
} | ||
|
||
private: | ||
/// @brief The rotation part of the transformation | ||
Rotation rotation_; | ||
|
||
/// @brief The translation part of the transformation | ||
Translation translation_; | ||
}; | ||
|
||
/// @brief Apply a transformation to a mesh | ||
class MeshTransformation | ||
{ | ||
public: | ||
/// @brief Apply a transformation to a mesh with a Cartesian projection | ||
template <TransformationFunction Transformation> | ||
static void Compute(Mesh& mesh, Transformation transformation) | ||
{ | ||
if (mesh.m_projection != transformation.TransformationProjection()) | ||
{ | ||
throw MeshKernelError("Incorrect mesh coordinate system, expecting '{}', found '{}'", | ||
ToString(transformation.TransformationProjection()), ToString(mesh.m_projection)); | ||
} | ||
|
||
#pragma omp parallel for | ||
for (int i = 0; i < static_cast<int>(mesh.GetNumNodes()); ++i) | ||
{ | ||
if (mesh.m_nodes[i].IsValid()) | ||
{ | ||
mesh.m_nodes[i] = transformation(mesh.m_nodes[i]); | ||
} | ||
} | ||
} | ||
}; | ||
|
||
} // namespace meshkernel |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Oops, something went wrong.
Oops, something went wrong.
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
for consistency we should use m_rotation, although i like rotation_ more for alphabetical sorting