-
Notifications
You must be signed in to change notification settings - Fork 1k
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
This is an incomplete commit. Establishes SymmetryTransformerGenerator.
Beware, the option to optionally use StitchedMeshGenerator has not been tested. Tests have not been written. I would appreciate it if the test currently in simple.i would end up in the documentation as an example of what default parameters are ran when the stitch option is exercised.
- Loading branch information
1 parent
04e909d
commit 492bbba
Showing
9 changed files
with
334 additions
and
0 deletions.
There are no files selected for viewing
24 changes: 24 additions & 0 deletions
24
framework/doc/content/source/meshgenerators/SymmetryTransformerGenerator.md
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,24 @@ | ||
# SymmetryTransformerGenerator | ||
|
||
!syntax description /Mesh/SymmetryTransformerGenerator | ||
|
||
## Overview | ||
|
||
The SymmetryTransformerGenerator makes a mirror reflection of a mesh across an arbitrary plane or line (supplied by the user). All input is expected to be three dimensional even if the mesh in question is two dimensional; in such a case, let the z component be 0 (e.g., `extrusion_vector = '1 1 0'`). The values of the components can be floating types, not just integers. | ||
|
||
The user sets the plane that will be reflected over by giving two vectors: a vector that gives the position of any given point on the line/plane from the origin; and, a vector that is normal (aka perpendicular/ orthogonal) to said line/plane. The normal vector establishes the slope of the plane of reflection. | ||
|
||
Internally, SymmetryTransformerGenerator applies a matrix operation to the vectors the user supplied. The matrix that is used assumed that the inputted normal vector is also a unit vector, too (meaning, the length of the vector is 1). However, it is impractical to ask that the user give the x,y, and z components of a perfect normal unit vector. The user would have to calculate the coordiantes to a high precision to prevent arithmetic rounding from calculating a norm (length) of not exactly 1. | ||
|
||
For example, if the user wanted a give a normal unit vector at 45° angle, even if they entered x and y values to the 10th decimal place of precision (0.7071067811), the norm of the inputted vector would be calculated to be 0.99999999987760335. The maximum decimal places of precision the user can enter is limited by the operating system and compiler used to build MOOSE. The user would not be able to enter some extremely high precision number even if they wanted to (on the author’s machine, up to 17 decimals of precision are accepted). | ||
For this reason, the user is only expected to enter a normal vector, which is automatically converted to a unit normal vector. While unexpected, it is theoretically possible if the user is dealing with very small, precise areas for arithmetic error to be introduced in the calculation of the unit normal vector. In this case, adjust the inputted normal vector. | ||
|
||
!alert warning | ||
No treatment is made on the internally-kept order of nodes in the mirrored mesh, so the mirrored mesh will have a negative connectivity/volume! | ||
|
||
|
||
!syntax parameters /Mesh/SymmetryTransformerGenerator | ||
|
||
!syntax inputs /Mesh/SymmetryTransformerGenerator | ||
|
||
!syntax children /Mesh/SymmetryTransformerGenerator |
35 changes: 35 additions & 0 deletions
35
framework/include/meshgenerators/SymmetryTransformerGenerator.h
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,35 @@ | ||
//* This file is part of the MOOSE framework | ||
//* https://www.mooseframework.org | ||
//* | ||
//* All rights reserved, see COPYRIGHT for full restrictions | ||
//* https://github.com/idaholab/moose/blob/master/COPYRIGHT | ||
//* | ||
//* Licensed under LGPL 2.1, please see LICENSE for details | ||
//* https://www.gnu.org/licenses/lgpl-2.1.html | ||
|
||
#pragma once | ||
|
||
#include "MeshGenerator.h" | ||
|
||
/* | ||
* A mesh generator that applies a linear transformation (rotation, translation) to the mesh | ||
*/ | ||
class SymmetryTransformerGenerator : public MeshGenerator | ||
{ | ||
public: | ||
static InputParameters validParams(); | ||
|
||
SymmetryTransformerGenerator(const InputParameters & parameters); | ||
|
||
std::unique_ptr<MeshBase> generate() override; | ||
|
||
protected: | ||
/// the input mesh | ||
std::unique_ptr<MeshBase> & _input; | ||
|
||
/// the mirror around which to transform the mesh | ||
RealEigenVector _mirror_point_vector; | ||
RealEigenVector _mirror_normal_vector; | ||
|
||
std::vector<std::vector<std::string>> _stitch_boundaries_pairs; | ||
}; |
113 changes: 113 additions & 0 deletions
113
framework/src/meshgenerators/SymmetryTransformerGenerator.C
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,113 @@ | ||
//* This file is part of the MOOSE framework | ||
//* https://www.mooseframework.org | ||
//* | ||
//* All rights reserved, see COPYRIGHT for full restrictions | ||
//* https://github.com/idaholab/moose/blob/master/COPYRIGHT | ||
//* | ||
//* Licensed under LGPL 2.1, please see LICENSE for details | ||
//* https://www.gnu.org/licenses/lgpl-2.1.html | ||
|
||
#include "SymmetryTransformerGenerator.h" | ||
#include "CastUniquePointer.h" | ||
|
||
|
||
registerMooseObject("MooseApp", SymmetryTransformerGenerator); | ||
|
||
InputParameters | ||
SymmetryTransformerGenerator::validParams() | ||
{ | ||
InputParameters params = MeshGenerator::validParams(); | ||
|
||
params.addRequiredParam<MeshGeneratorName>("input", "The mesh we want to modify"); | ||
params.addClassDescription("Applies a mirror transform to the entire mesh."); | ||
params.addRequiredParam<RealEigenVector>( | ||
"mirror_point", | ||
"Any point on the plane/line over which the reflection operation will be done"); | ||
params.addRequiredParam<RealEigenVector>( | ||
"mirror_normal_vector", | ||
"A vector normal to (perpendicular/orthogonal to) the plane/line over which the " | ||
"reflection operation will be done"); | ||
params.addParam<std::vector<std::vector<std::string>>>( | ||
" ", | ||
std::vector<std::vector<std::string>>(), | ||
"Pairs of boundaries to be stitched together between the 1st mesh in inputs and each " | ||
"consecutive mesh"); | ||
return params; | ||
} | ||
|
||
SymmetryTransformerGenerator::SymmetryTransformerGenerator(const InputParameters & parameters) | ||
: MeshGenerator(parameters), | ||
_input(getMesh("input")), | ||
_mirror_point_vector(getParam<RealEigenVector>("mirror_point")), | ||
_mirror_normal_vector(getParam<RealEigenVector>("mirror_normal_vector")), | ||
_stitch_boundaries_pairs( | ||
getParam<std::vector<std::vector<std::string>>>("stitch_boundaries_pairs")) | ||
{ | ||
// enforce 3D coordinates | ||
if (_mirror_point_vector.size() != 3) | ||
mooseError("mirror_point should be 3d vectors, but a dimension of ", | ||
_mirror_point_vector.size(), | ||
"was entered instead, respectively. If you are working in 2D, let the 3rd component" | ||
"of your vectors be zero."); | ||
|
||
if (_mirror_normal_vector.size() != 3) | ||
mooseError(" mirror_normal_vector should be 3d vectors, but a dimension of ", | ||
_mirror_normal_vector.size(), | ||
"was entered instead, respectively. If you are working in 2D, let the 3rd component" | ||
"of your vectors be zero."); | ||
|
||
// convert normal vector into a unit normal vector | ||
double nrm = _mirror_normal_vector.norm(); | ||
_mirror_normal_vector << _mirror_normal_vector[0] / nrm, _mirror_normal_vector[1] / nrm, | ||
_mirror_normal_vector[2] / nrm; | ||
} | ||
|
||
std::unique_ptr<MeshBase> | ||
SymmetryTransformerGenerator::generate() | ||
{ | ||
std::unique_ptr<MeshBase> mesh = std::move(_input); | ||
|
||
// https://en.wikipedia.org/wiki/Transformation_matrix#Reflection_2 | ||
// variables renamed for readability and verification | ||
double a = _mirror_normal_vector[0], b = _mirror_normal_vector[1], c = _mirror_normal_vector[2], | ||
d = ((RealEigenVector)(-1 * _mirror_point_vector.transpose() * _mirror_normal_vector))(0); | ||
|
||
RealEigenMatrix mirror_transformation(4, 4); | ||
mirror_transformation << (1 - 2 * a * a), (-2 * a * b), (-2 * a * c), (-2 * a * d), (-2 * a * b), | ||
(1 - 2 * b * b), (-2 * b * c), (-2 * b * d), (-2 * a * c), (-2 * b * c), (1 - 2 * c * c), | ||
(-2 * c * d), (0), (0), (0), (1); | ||
|
||
for (auto & node : mesh->node_ptr_range()) | ||
{ | ||
RealEigenVector location_vec(4); | ||
location_vec << (*node)(0), (*node)(1), (*node)(2), 1; | ||
|
||
location_vec = mirror_transformation * location_vec; | ||
|
||
// MOOSE uses libmesh in a 3 dim only mode, therefore we assume 3D here | ||
(*node)(0) = location_vec(0); | ||
(*node)(1) = location_vec(1); | ||
(*node)(2) = location_vec(2); | ||
} | ||
|
||
if (_stitch_boundaries_pairs.size() > 0) | ||
{ | ||
auto params = _app.getFactory().getValidParams("StitchedMeshGenerator"); | ||
|
||
// order of vector elements matters for this generator | ||
// here order by: original mesh first, our custom mesh second | ||
params.set<std::vector<MeshGeneratorName>>("inputs") = {getParam<MeshGeneratorName>("input"), | ||
name()}; | ||
|
||
// params.set<std::vector<std::vector<std::string>>>("stitch_boundaries_pairs") = { | ||
// {_sideset_name, _SIDESET_TO_BE_STITCHED}}; | ||
params.set<std::vector<std::vector<std::string>>>("stitch_boundaries_pairs") = | ||
_stitch_boundaries_pairs; | ||
|
||
// stitch the newly made high-dimensional mesh back to the original mesh | ||
return dynamic_pointer_cast<MeshBase>( | ||
addMeshSubgenerator("StitchedMeshGenerator", name() + "_stitchedMeshGenerator", params)); | ||
} | ||
|
||
return mesh; | ||
} |
60 changes: 60 additions & 0 deletions
60
test/tests/meshgenerators/symmetry_transformer_generator/rotate_and_scale.i
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,60 @@ | ||
[Mesh] | ||
[./fmg] | ||
type = FileMeshGenerator | ||
file = cylinder.e | ||
[] | ||
|
||
[./rotate] | ||
type = TransformGenerator | ||
input = fmg | ||
transform = ROTATE | ||
vector_value = '0 90 0' | ||
[] | ||
|
||
[./scale] | ||
type = TransformGenerator | ||
input = rotate | ||
transform = SCALE | ||
vector_value ='1e2 1e2 1e2' | ||
[] | ||
[] | ||
|
||
[Variables] | ||
[./u] | ||
order = FIRST | ||
family = LAGRANGE | ||
[../] | ||
[] | ||
|
||
[Kernels] | ||
[./diff] | ||
type = Diffusion | ||
variable = u | ||
[../] | ||
[] | ||
|
||
[BCs] | ||
[./left] | ||
type = DirichletBC | ||
variable = u | ||
boundary = 1 | ||
value = 0 | ||
[../] | ||
|
||
[./right] | ||
type = DirichletBC | ||
variable = u | ||
boundary = 2 | ||
value = 1 | ||
[../] | ||
[] | ||
|
||
[Executioner] | ||
type = Steady | ||
|
||
solve_type = 'PJFNK' | ||
[] | ||
|
||
[Outputs] | ||
exodus = true | ||
[] |
21 changes: 21 additions & 0 deletions
21
test/tests/meshgenerators/symmetry_transformer_generator/simple.i
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,21 @@ | ||
[Mesh] | ||
# [file] | ||
# type = FileMeshGenerator | ||
# file = reactor.e | ||
# [] | ||
[file] | ||
type = GeneratedMeshGenerator | ||
dim = 2 | ||
[] | ||
[mirror] | ||
type = SymmetryTransformerGenerator | ||
input = file | ||
mirror_point = "0 1 0" | ||
mirror_normal_vector = "0 1 0" | ||
[] | ||
[stitch] | ||
type = StitchedMeshGenerator | ||
inputs = 'file mirror' | ||
stitch_boundaries_pairs = 'top top' | ||
[] | ||
[] |
34 changes: 34 additions & 0 deletions
34
test/tests/meshgenerators/symmetry_transformer_generator/tests
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,34 @@ | ||
[Tests] | ||
design = 'meshgenerators/SymmetryTransformerGenerator.md' | ||
issues = ' #21578' | ||
|
||
[rotate_and_scale] | ||
type = 'Exodiff' | ||
input = '.i' | ||
exodiff = '_in.e' | ||
requirement = "The system shall include the ability to mirror a finite element mesh." | ||
cli_args = '--mesh-only' | ||
recover = false | ||
[] | ||
|
||
[translate] | ||
requirement = "The system shall include the ability to " | ||
|
||
[user_set] | ||
type = 'Exodiff' | ||
input = 'translate.i' | ||
exodiff = 'translate_in.e' | ||
cli_args = '--mesh-only' | ||
recover = false | ||
detail = 'do this, ' | ||
[] | ||
[center_origin] | ||
type = 'Exodiff' | ||
input = '.i' | ||
exodiff = '_in.e' | ||
cli_args = '--mesh-only' | ||
recover = false | ||
detail = 'or that' | ||
[] | ||
[] | ||
[] |
15 changes: 15 additions & 0 deletions
15
test/tests/meshgenerators/symmetry_transformer_generator/translate.i
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,15 @@ | ||
[Mesh] | ||
[gmg] | ||
type = GeneratedMeshGenerator | ||
dim = 2 | ||
nx = 2 | ||
ny = 2 | ||
[] | ||
|
||
[translate] | ||
type = TransformGenerator | ||
input = gmg | ||
transform = translate | ||
vector_value = '1 2 0' | ||
[] | ||
[] |
14 changes: 14 additions & 0 deletions
14
test/tests/meshgenerators/symmetry_transformer_generator/translate_center_origin.i
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,14 @@ | ||
[Mesh] | ||
[gmg] | ||
type = GeneratedMeshGenerator | ||
dim = 2 | ||
nx = 2 | ||
ny = 2 | ||
[] | ||
|
||
[translate] | ||
type = TransformGenerator | ||
input = gmg | ||
transform = translate_center_origin | ||
[] | ||
[] |
18 changes: 18 additions & 0 deletions
18
test/tests/meshgenerators/symmetry_transformer_generator/translate_min_origin.i
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,18 @@ | ||
[Mesh] | ||
[gmg] | ||
type = GeneratedMeshGenerator | ||
dim = 2 | ||
nx = 2 | ||
ny = 2 | ||
xmin = 1 | ||
xmax = 2 | ||
ymin = 3 | ||
ymax = 4 | ||
[] | ||
|
||
[translate] | ||
type = TransformGenerator | ||
input = gmg | ||
transform = translate_min_origin | ||
[] | ||
[] |