1 /*---------------------------------------------------------------------------*\
3 \\ / F ield | foam-extend: Open Source CFD
4 \\ / O peration | Version: 3.2
5 \\ / A nd | Web: http://www.foam-extend.org
6 \\/ M anipulation | For copyright notice see file Copyright
7 -------------------------------------------------------------------------------
9 This file is part of foam-extend.
11 foam-extend is free software: you can redistribute it and/or modify it
12 under the terms of the GNU General Public License as published by the
13 Free Software Foundation, either version 3 of the License, or (at your
14 option) any later version.
16 foam-extend is distributed in the hope that it will be useful, but
17 WITHOUT ANY WARRANTY; without even the implied warranty of
18 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
19 General Public License for more details.
21 You should have received a copy of the GNU General Public License
22 along with foam-extend. If not, see <http://www.gnu.org/licenses/>.
25 Generalized grid interface (GGI) patch, providing coupling
26 between arbitrary patches which belong to the same fvMesh
29 Hrvoje Jasak, Wikki Ltd. All rights reserved
32 Martin Beaudoin, Hydro-Quebec, (2008)
34 \*---------------------------------------------------------------------------*/
36 #include "ggiFvPatch.H"
37 #include "addToRunTimeSelectionTable.H"
38 #include "fvBoundaryMesh.H"
40 // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
44 defineTypeNameAndDebug(ggiFvPatch, 0);
45 addToRunTimeSelectionTable(fvPatch, ggiFvPatch, polyPatch);
49 // * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * //
51 Foam::ggiFvPatch::~ggiFvPatch()
55 // * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * * //
57 // Make patch weighting factors
58 void Foam::ggiFvPatch::makeWeights(scalarField& w) const
60 // Calculation of weighting factors is performed from the master
61 // position, using reconstructed shadow cell centres
63 if (ggiPolyPatch_.master())
67 // Note: mag in the dot-product.
68 // For all valid meshes, the non-orthogonality will be less than
69 // 90 deg and the dot-product will be positive. For invalid
70 // meshes (d & s <= 0), this will stabilise the calculation
71 // but the result will be poor. HJ, 24/Aug/2011
73 mag(n & (ggiPolyPatch_.reconFaceCellCentres() - Cf()));
75 w = nfc/(mag(n & (Cf() - Cn())) + nfc);
79 // Set overlap weights to 0.5 and use mirrored neighbour field
80 // for interpolation. HJ, 21/Jan/2009
81 bridge(scalarField(size(), 0.5), w);
86 // Pick up weights from the master side
87 scalarField masterWeights(shadow().size());
88 shadow().makeWeights(masterWeights);
90 scalarField oneMinusW = 1 - masterWeights;
92 w = interpolate(oneMinusW);
96 // Set overlap weights to 0.5 and use mirrored neighbour field
97 // for interpolation. HJ, 21/Jan/2009
98 bridge(scalarField(size(), 0.5), w);
104 // Make patch face - neighbour cell distances
105 void Foam::ggiFvPatch::makeDeltaCoeffs(scalarField& dc) const
107 if (ggiPolyPatch_.master())
109 // Stabilised form for bad meshes. HJ, 24/Aug/2011
110 vectorField d = delta();
112 dc = 1.0/max(nf() & d, 0.05*mag(d));
116 scalarField bridgeDeltas = nf() & fvPatch::delta();
118 bridge(bridgeDeltas, dc);
123 scalarField masterDeltas(shadow().size());
124 shadow().makeDeltaCoeffs(masterDeltas);
125 dc = interpolate(masterDeltas);
129 scalarField bridgeDeltas = nf() & fvPatch::delta();
131 bridge(bridgeDeltas, dc);
137 // Make patch face non-orthogonality correction vectors
138 void Foam::ggiFvPatch::makeCorrVecs(vectorField& cv) const
140 // Non-orthogonality correction on a ggi interface
143 // Calculate correction vectors on coupled patches
144 const scalarField& patchDeltaCoeffs = deltaCoeffs();
146 vectorField patchDeltas = delta();
147 vectorField n = nf();
149 // If non-orthogonality is over 90 deg, kill correction vector
151 cv = pos(patchDeltas & n)*(n - patchDeltas*patchDeltaCoeffs);
155 // Return delta (P to N) vectors across coupled patch
156 Foam::tmp<Foam::vectorField> Foam::ggiFvPatch::delta() const
158 if (ggiPolyPatch_.master())
160 tmp<vectorField> tDelta = ggiPolyPatch_.reconFaceCellCentres() - Cn();
164 vectorField bridgeDeltas = Cf() - Cn();
166 bridge(bridgeDeltas, tDelta());
173 tmp<vectorField> tDelta = interpolate
175 shadow().Cn() - ggiPolyPatch_.shadow().reconFaceCellCentres()
180 vectorField bridgeDeltas = Cf() - Cn();
182 bridge(bridgeDeltas, tDelta());
190 const Foam::ggiFvPatch& Foam::ggiFvPatch::shadow() const
192 const fvPatch& p = this->boundaryMesh()[ggiPolyPatch_.shadowIndex()];
194 return refCast<const ggiFvPatch>(p);
198 bool Foam::ggiFvPatch::master() const
200 return ggiPolyPatch_.master();
204 bool Foam::ggiFvPatch::fineLevel() const
210 Foam::label Foam::ggiFvPatch::shadowIndex() const
212 return ggiPolyPatch_.shadowIndex();
216 const Foam::ggiLduInterface& Foam::ggiFvPatch::shadowInterface() const
218 const fvPatch& p = this->boundaryMesh()[ggiPolyPatch_.shadowIndex()];
220 return refCast<const ggiLduInterface>(p);
224 Foam::label Foam::ggiFvPatch::zoneSize() const
226 return ggiPolyPatch_.zone().size();
230 const Foam::labelList& Foam::ggiFvPatch::zoneAddressing() const
232 return ggiPolyPatch_.zoneAddressing();
236 const Foam::labelListList& Foam::ggiFvPatch::addressing() const
238 if (ggiPolyPatch_.master())
240 return ggiPolyPatch_.patchToPatch().masterAddr();
244 return ggiPolyPatch_.patchToPatch().slaveAddr();
249 bool Foam::ggiFvPatch::localParallel() const
251 return ggiPolyPatch_.localParallel();
255 const Foam::scalarListList& Foam::ggiFvPatch::weights() const
257 if (ggiPolyPatch_.master())
259 return ggiPolyPatch_.patchToPatch().masterWeights();
263 return ggiPolyPatch_.patchToPatch().slaveWeights();
268 Foam::tmp<Foam::labelField> Foam::ggiFvPatch::interfaceInternalField
270 const unallocLabelList& internalData
273 return patchInternalField(internalData);
277 void Foam::ggiFvPatch::initTransfer
279 const Pstream::commsTypes commsType,
280 const unallocLabelList& interfaceData
283 labelTransferBuffer_ = interfaceData;
287 Foam::tmp<Foam::labelField> Foam::ggiFvPatch::transfer
289 const Pstream::commsTypes,
290 const unallocLabelList& interfaceData
293 return this->shadow().labelTransferBuffer();
297 void Foam::ggiFvPatch::initInternalFieldTransfer
299 const Pstream::commsTypes commsType,
300 const unallocLabelList& iF
303 labelTransferBuffer_ = patchInternalField(iF);
307 Foam::tmp<Foam::labelField> Foam::ggiFvPatch::internalFieldTransfer
309 const Pstream::commsTypes,
310 const unallocLabelList& iF
313 return shadow().labelTransferBuffer();
318 // ************************************************************************* //