dynamicMotionSolverFvMeshAMI.C
Go to the documentation of this file.
1 /*---------------------------------------------------------------------------*\
2  ========= |
3  \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
4  \\ / O peration |
5  \\ / A nd | www.openfoam.com
6  \\/ M anipulation |
7 -------------------------------------------------------------------------------
8  Copyright (C) 2019-2022 OpenCFD Ltd.
9 -------------------------------------------------------------------------------
10 License
11  This file is part of OpenFOAM.
12 
13  OpenFOAM is free software: you can redistribute it and/or modify it
14  under the terms of the GNU General Public License as published by
15  the Free Software Foundation, either version 3 of the License, or
16  (at your option) any later version.
17 
18  OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
19  ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
20  FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
21  for more details.
22 
23  You should have received a copy of the GNU General Public License
24  along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>.
25 
26 \*---------------------------------------------------------------------------*/
27 
30 #include "motionSolver.H"
31 #include "volFields.H"
32 #include "surfaceFields.H"
33 #include "cyclicAMIPolyPatch.H"
34 #include "polyTopoChange.H"
35 #include "MeshObject.H"
36 #include "lduMesh.H"
37 #include "surfaceInterpolate.H"
38 
39 #include "processorFvPatch.H"
40 
41 // * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * //
42 
43 namespace Foam
44 {
45  defineTypeNameAndDebug(dynamicMotionSolverFvMeshAMI, 0);
47  (
48  dynamicFvMesh,
49  dynamicMotionSolverFvMeshAMI,
50  IOobject
51  );
53  (
54  dynamicFvMesh,
55  dynamicMotionSolverFvMeshAMI,
56  doInit
57  );
58 }
59 
60 
61 // * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * //
62 
63 Foam::dynamicMotionSolverFvMeshAMI::dynamicMotionSolverFvMeshAMI
64 (
65  const IOobject& io,
66  const bool doInit
67 )
68 :
69  dynamicFvMesh(io, doInit)
70 {
71  if (doInit)
72  {
73  init(false); // do not initialise lower levels
74  }
75 }
76 
77 
78 bool Foam::dynamicMotionSolverFvMeshAMI::init(const bool doInit)
79 {
80  if (doInit)
81  {
82  dynamicFvMesh::init(doInit);
83  }
84 
85  motionPtr_ = motionSolver::New(*this);
86  return true;
87 }
88 
89 
90 Foam::dynamicMotionSolverFvMeshAMI::dynamicMotionSolverFvMeshAMI
91 (
92  const IOobject& io,
94  faceList&& faces,
95  labelList&& allOwner,
96  labelList&& allNeighbour,
97  const bool syncPar
98 )
99 :
101  (
102  io,
103  std::move(points),
104  std::move(faces),
105  std::move(allOwner),
106  std::move(allNeighbour),
107  syncPar
108  ),
109  motionPtr_(motionSolver::New(*this))
110 {}
111 
112 
113 // * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
116 {
117  return *motionPtr_;
118 }
119 
120 
122 {
123  // Mesh not moved/changed yet
124  moving(false);
125  topoChanging(false);
126 
127  if (debug)
128  {
129  for (const fvPatch& fvp : boundary())
130  {
131  if (!isA<processorFvPatch>(fvp))
132  {
133  Info<< "1 --- patch:" << fvp.patch().name()
134  << " area:" << gSum(fvp.magSf()) << endl;
135  }
136  }
137  }
138 
139  pointField newPoints(motionPtr_->curPoints());
140 
141  polyBoundaryMesh& pbm = const_cast<polyBoundaryMesh&>(boundaryMesh());
142 
143  // Scan all patches and see if we want to apply a mesh topology update
144  bool changeRequired = false;
145  for (label patchi = 0; patchi < pbm.nNonProcessor(); ++patchi)
146  {
147  const polyPatch& pp = pbm[patchi];
148 
149  DebugInfo
150  << "pre-topology change: patch " << pp.name()
151  << " size:" << returnReduce(pp.size(), sumOp<label>())
152  << " mag(faceAreas):" << gSum(mag(pp.faceAreas())) << endl;
153 
154  //changeRequired = pp.changeTopology(newPoints) || changeRequired;
155  changeRequired = pp.changeTopology() || changeRequired;
156  }
157 
158  if (returnReduceOr(changeRequired))
159  {
160  polyTopoChange polyTopo(*this);
161 
162  // Set new point positions in polyTopo object
163  polyTopo.movePoints(newPoints);
164 
165  // Accumulate the patch-based mesh changes on the current mesh
166  // Note:
167  // - updates the AMIs using the new points
168  // - creates a topo change object that removes old added faces and
169  // adds the new faces
170  for (polyPatch& pp : pbm)
171  {
172  pp.setTopology(polyTopo);
173  }
174 
175  // Update geometry
176  // Note
177  // - changeMesh leads to polyMesh::resetPrimitives which will also
178  // trigger polyBoundaryMesh::updateMesh (init and update) and
179  // ::calcGeometry (with topoChanging = false)
180  // - BUT: mesh still corresponds to original (non-extended mesh) so
181  // we want to bypass these calls...
182  // - after changes topoChanging = true
183  autoPtr<mapPolyMesh> map =
184  polyTopo.changeMesh
185  (
186  *this,
187  true // We will be calling movePoints after this update
188  );
189 
190  // Apply topology change - update fv geometry and map fields
191  // - polyMesh::updateMesh
192  // - fires initUpdateMesh and updateMesh in AMI BCs - called before
193  // mapFields
194  // - AMI addressing must be up-to-date - used by, e.g. FaceCellWave
195  // - will trigger (again) polyBoundaryMesh::updateMesh (init and update)
196  updateMesh(map());
197 
198  // Move points and update derived properties
199  // Note:
200  // - resets face areas based on raw point locations!
201  // - polyBoundaryMesh::updateMesh (init and update)
202  // Note:
203  // - processorPolyPatches will trigger calculation of faceCentres
204  // (and therefore cell volumes), so need to update faceAreas in
205  // initMovePoints since proc patches will be evaluated later than
206  // AMI patches
207  if (map().hasMotionPoints())
208  {
209  movePoints(map().preMotionPoints());
210  }
211  }
212  else
213  {
214  fvMesh::movePoints(newPoints);
215  }
216 
217  volVectorField* Uptr = getObjectPtr<volVectorField>("U");
218 
219  if (Uptr)
220  {
222 
223  surfaceVectorField* UfPtr = getObjectPtr<surfaceVectorField>("Uf");
224  if (UfPtr)
225  {
226  *UfPtr = fvc::interpolate(*Uptr);
227  }
228  }
229 
230  if (debug)
231  {
232  for (const fvPatch& fvp : boundary())
233  {
234  if (!isA<processorFvPatch>(fvp))
235  {
236  Info<< "2 --- patch:" << fvp.patch().name()
237  << " area:" << gSum(fvp.magSf()) << endl;
238  }
239  }
240  }
241 
242  return true;
243 }
244 
245 
246 // ************************************************************************* //
Foam::surfaceFields.
faceListList boundary
const Field< point_type > & faceAreas() const
Return face area vectors for patch.
const polyBoundaryMesh & pbm
virtual bool update()
Update the mesh for both mesh motion and topology change.
dimensioned< typename typeOfMag< Type >::type > mag(const dimensioned< Type > &dt)
GeometricField< vector, fvsPatchField, surfaceMesh > surfaceVectorField
Ostream & endl(Ostream &os)
Add newline and flush stream.
Definition: Ostream.H:531
A finiteVolume patch using a polyPatch and a fvBoundaryMesh.
Definition: fvPatch.H:70
tmp< DimensionedField< TypeR, GeoMesh > > New(const tmp< DimensionedField< TypeR, GeoMesh >> &tf1, const word &name, const dimensionSet &dimensions, const bool initCopy=false)
Global function forwards to reuseTmpDimensionedField::New.
virtual bool movePoints()
Do what is necessary if the mesh has moved.
Virtual base class for mesh motion solver.
Definition: motionSolver.H:54
virtual bool init(const bool doInit)
Initialise all non-demand-driven data.
Definition: dynamicFvMesh.C:84
static autoPtr< motionSolver > New(const polyMesh &)
Select constructed from polyMesh.
Definition: motionSolver.C:143
GeometricField< vector, fvPatchField, volMesh > volVectorField
Definition: volFieldsFwd.H:82
T returnReduce(const T &value, const BinaryOp &bop, const int tag=UPstream::msgType(), const label comm=UPstream::worldComm)
Perform reduction on a copy, using specified binary operation.
const motionSolver & motion() const
Return the motionSolver.
Macros for easy insertion into run-time selection tables.
vectorField pointField
pointField is a vectorField.
Definition: pointFieldFwd.H:38
Type gSum(const FieldField< Field, Type > &f)
const pointField & points
#define DebugInfo
Report an information message using Foam::Info.
int debug
Static debugging option.
defineTypeNameAndDebug(combustionModel, 0)
static tmp< GeometricField< Type, fvsPatchField, surfaceMesh > > interpolate(const GeometricField< Type, fvPatchField, volMesh > &tvf, const surfaceScalarField &faceFlux, Istream &schemeData)
Interpolate field onto faces using scheme given by Istream.
Abstract base class for geometry and/or topology changing fvMesh.
Definition: dynamicFvMesh.H:74
void correctBoundaryConditions()
Correct boundary field.
messageStream Info
Information stream (stdout output on master, null elsewhere)
IOobject io("surfaceFilmProperties", mesh.time().constant(), mesh, IOobject::READ_IF_PRESENT, IOobject::NO_WRITE, IOobject::NO_REGISTER)
label nNonProcessor() const
The number of patches before the first processor patch.
bool returnReduceOr(const bool value, const label comm=UPstream::worldComm)
Perform logical (or) MPI Allreduce on a copy. Uses UPstream::reduceOr.
Defines the attributes of an object for which implicit objectRegistry management is supported...
Definition: IOobject.H:172
virtual bool init(const bool doInit)
Initialise all non-demand-driven data.
uindirectPrimitivePatch pp(UIndirectList< face >(mesh.faces(), faceLabels), mesh.points())
Namespace for OpenFOAM.
addToRunTimeSelectionTable(functionObject, pointHistory, dictionary)