FreeFOAM The Cross-Platform CFD Toolkit
directMappedFixedValueFvPatchField.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 | Copyright (C) 1991-2010 OpenCFD Ltd.
6  \\/ M anipulation |
7 -------------------------------------------------------------------------------
8 License
9  This file is part of OpenFOAM.
10 
11  OpenFOAM is free software: you can redistribute it and/or modify it
12  under the terms of the GNU General Public License as published by
13  the Free Software Foundation, either version 3 of the License, or
14  (at your option) any later version.
15 
16  OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
17  ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
18  FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
19  for more details.
20 
21  You should have received a copy of the GNU General Public License
22  along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>.
23 
24 \*---------------------------------------------------------------------------*/
25 
28 #include <finiteVolume/volFields.H>
29 #include <OpenFOAM/mapDistribute.H>
30 
31 // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
32 
33 namespace Foam
34 {
35 
36 // * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * //
37 
38 template<class Type>
40 (
41  const fvPatch& p,
43 )
44 :
46  setAverage_(false),
47  average_(pTraits<Type>::zero)
48 {}
49 
50 
51 template<class Type>
53 (
55  const fvPatch& p,
57  const fvPatchFieldMapper& mapper
58 )
59 :
60  fixedValueFvPatchField<Type>(ptf, p, iF, mapper),
61  setAverage_(ptf.setAverage_),
62  average_(ptf.average_)
63 {
64  if (!isA<directMappedPatchBase>(this->patch().patch()))
65  {
67  (
68  "directMappedFixedValueFvPatchField<Type>::"
69  "directMappedFixedValueFvPatchField\n"
70  "(\n"
71  " const directMappedFixedValueFvPatchField<Type>&,\n"
72  " const fvPatch&,\n"
73  " const Field<Type>&,\n"
74  " const fvPatchFieldMapper&\n"
75  ")\n"
76  ) << "\n patch type '" << p.type()
77  << "' not type '" << directMappedPatchBase::typeName << "'"
78  << "\n for patch " << p.name()
79  << " of field " << this->dimensionedInternalField().name()
80  << " in file " << this->dimensionedInternalField().objectPath()
81  << exit(FatalError);
82  }
83 }
84 
85 
86 template<class Type>
88 (
89  const fvPatch& p,
91  const dictionary& dict
92 )
93 :
95  setAverage_(readBool(dict.lookup("setAverage"))),
96  average_(pTraits<Type>(dict.lookup("average")))
97 {
98  if (!isA<directMappedPatchBase>(this->patch().patch()))
99  {
101  (
102  "directMappedFixedValueFvPatchField<Type>::"
103  "directMappedFixedValueFvPatchField\n"
104  "(\n"
105  " const fvPatch& p,\n"
106  " const DimensionedField<Type, volMesh>& iF,\n"
107  " const dictionary& dict\n"
108  ")\n"
109  ) << "\n patch type '" << p.type()
110  << "' not type '" << directMappedPatchBase::typeName << "'"
111  << "\n for patch " << p.name()
112  << " of field " << this->dimensionedInternalField().name()
113  << " in file " << this->dimensionedInternalField().objectPath()
114  << exit(FatalError);
115  }
116 
118  //const directMappedPatchBase& mpp = refCast<const directMappedPatchBase>
119  //(
120  // this->patch().patch()
121  //);
122  //(void)mpp.map().schedule();
123 }
124 
125 
126 template<class Type>
128 (
130 )
131 :
133  setAverage_(ptf.setAverage_),
134  average_(ptf.average_)
135 {}
136 
137 
138 template<class Type>
140 (
143 )
144 :
146  setAverage_(ptf.setAverage_),
147  average_(ptf.average_)
148 {}
149 
150 
151 // * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
152 
153 template<class Type>
155 {
156  if (this->updated())
157  {
158  return;
159  }
160 
162 
163  // Get the scheduling information from the directMappedPatchBase
164  const directMappedPatchBase& mpp = refCast<const directMappedPatchBase>
165  (
167  );
168  const mapDistribute& distMap = mpp.map();
169 
170  // Force recalculation of schedule
171  (void)distMap.schedule();
172 
173  const fvMesh& nbrMesh = refCast<const fvMesh>(mpp.sampleMesh());
174  const word& fldName = this->dimensionedInternalField().name();
175 
176  // Result of obtaining remote values
177  Field<Type> newValues;
178 
179  switch (mpp.mode())
180  {
182  {
183  if (mpp.sameRegion())
184  {
185  newValues = this->internalField();
186  }
187  else
188  {
189  newValues = nbrMesh.lookupObject<fieldType>
190  (
191  fldName
192  ).internalField();
193  }
195  (
197  distMap.schedule(),
198  distMap.constructSize(),
199  distMap.subMap(),
200  distMap.constructMap(),
201  newValues
202  );
203 
204  break;
205  }
207  {
208  const label nbrPatchID = nbrMesh.boundaryMesh().findPatchID
209  (
210  mpp.samplePatch()
211  );
212  if (nbrPatchID < 0)
213  {
215  (
216  "void directMappedFixedValueFvPatchField<Type>::"
217  "updateCoeffs()"
218  )<< "Unable to find sample patch " << mpp.samplePatch()
219  << " in region " << mpp.sampleRegion()
220  << " for patch " << this->patch().name() << nl
221  << abort(FatalError);
222  }
223 
224  const fieldType& nbrField = nbrMesh.lookupObject<fieldType>
225  (
226  fldName
227  );
228  newValues = nbrField.boundaryField()[nbrPatchID];
230  (
232  distMap.schedule(),
233  distMap.constructSize(),
234  distMap.subMap(),
235  distMap.constructMap(),
236  newValues
237  );
238 
239  break;
240  }
242  {
243  Field<Type> allValues(nbrMesh.nFaces(), pTraits<Type>::zero);
244 
245  const fieldType& nbrField = nbrMesh.lookupObject<fieldType>
246  (
247  fldName
248  );
249  forAll(nbrField.boundaryField(), patchI)
250  {
251  const fvPatchField<Type>& pf =
252  nbrField.boundaryField()[patchI];
253  label faceStart = pf.patch().patch().start();
254 
255  forAll(pf, faceI)
256  {
257  allValues[faceStart++] = pf[faceI];
258  }
259  }
260 
262  (
264  distMap.schedule(),
265  distMap.constructSize(),
266  distMap.subMap(),
267  distMap.constructMap(),
268  allValues
269  );
270 
271  newValues.transfer(allValues);
272 
273  break;
274  }
275  default:
276  {
278  (
279  "directMappedFixedValueFvPatchField<Type>::updateCoeffs()"
280  )<< "Unknown sampling mode: " << mpp.mode()
281  << nl << abort(FatalError);
282  }
283  }
284 
285  if (setAverage_)
286  {
287  Type averagePsi =
288  gSum(this->patch().magSf()*newValues)
289  /gSum(this->patch().magSf());
290 
291  if (mag(averagePsi)/mag(average_) > 0.5)
292  {
293  newValues *= mag(average_)/mag(averagePsi);
294  }
295  else
296  {
297  newValues += (average_ - averagePsi);
298  }
299  }
300 
301  this->operator==(newValues);
302 
303  if (debug)
304  {
305  Info<< "directMapped on field:" << fldName
306  << " patch:" << this->patch().name()
307  << " avg:" << gAverage(*this)
308  << " min:" << gMin(*this)
309  << " max:" << gMax(*this)
310  << endl;
311  }
312 
314 }
315 
316 
317 template<class Type>
319 {
321  os.writeKeyword("setAverage") << setAverage_ << token::END_STATEMENT << nl;
322  os.writeKeyword("average") << average_ << token::END_STATEMENT << nl;
323  this->writeEntry("value", os);
324 }
325 
326 
327 // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
328 
329 } // End namespace Foam
330 
331 // ************************ vim: set sw=4 sts=4 et: ************************ //