PDRsetFields.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) 2016 Shell Research Ltd.
9 Copyright (C) 2019-2021 OpenCFD Ltd.
10-------------------------------------------------------------------------------
11License
12 This file is part of OpenFOAM.
13
14 OpenFOAM is free software: you can redistribute it and/or modify it
15 under the terms of the GNU General Public License as published by
16 the Free Software Foundation, either version 3 of the License, or
17 (at your option) any later version.
18
19 OpenFOAM is distributed in the hope that it will be useful, but WITHOUT
20 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
21 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
22 for more details.
23
24 You should have received a copy of the GNU General Public License
25 along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>.
26
27Applications
28 PDRsetFields
29
30Description
31 Preparation of fields for PDRFoam
32
33SourceFiles
34 PDRsetFields.C
35
36\*---------------------------------------------------------------------------*/
37
38#include "argList.H"
39#include "Time.H"
40#include "IOdictionary.H"
41
42#include "PDRsetFields.H"
43#include "PDRlegacy.H"
44#include "PDRutils.H"
45#include "IOmanip.H"
46
47using namespace Foam;
48
49// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
50// Main program:
51
52int main(int argc, char* argv[])
53{
54 argList::addNote
55 (
56 "Processes a set of geometrical obstructions to determine the"
57 " equivalent blockage effects when setting cases for PDRFoam"
58 );
59 argList::noParallel();
60 argList::noFunctionObjects();
61
62 argList::addOption
63 (
64 "time",
65 "time",
66 "Specify a time"
67 );
68
69 argList::addOption("dict", "file", "Alternative PDRsetFieldsDict");
70
71 argList::addBoolOption
72 (
73 "legacy",
74 "Force use of legacy obstacles table"
75 );
76
77 argList::addDryRunOption
78 (
79 "Read obstacles and write VTK only"
80 );
81
82 #include "setRootCase.H"
83 #include "createTime.H"
84
85 const word dictName("PDRsetFieldsDict");
87
88 Info<< "Reading " << dictIO.name() << nl << endl;
89
90 IOdictionary setFieldsDict(dictIO);
91
92 const fileName& casepath = runTime.globalPath();
93
94 pars.timeName = "0";
96
97 // Program parameters (globals)
98 pars.read(setFieldsDict);
99
100 if (args.found("legacy"))
101 {
102 pars.legacyObsSpec = true;
103 }
104
105 // Always have the following:
106 // 0 = blockedFaces patch (no wall functions)
107 // 1 = mergingFaces patch
108 // 2 = wallFaces patch
109
111 patches.resize(PDRpatchDef::NUM_PREDEFINED);
112
113 for
114 (
116 {
117 PDRpatchDef::BLOCKED_FACE,
118 PDRpatchDef::MERGING_PATCH,
119 PDRpatchDef::WALL_PATCH,
120 }
121 )
122 {
123 patches[predef] = PDRpatchDef::names[predef];
124 }
125
126
127 // Dimensions and grid points for i-j-k domain
128 PDRblock pdrBlock;
129
131 {
132 PDRlegacy::read_mesh_spec(casepath, pdrBlock);
133 }
134 else
135 {
136 IOdictionary iodict
137 (
139 (
140 "PDRblockMeshDict",
141 runTime.system(),
142 runTime,
143 IOobject::MUST_READ_IF_MODIFIED,
144 IOobject::NO_WRITE
145 )
146 );
147
148 pdrBlock.read(iodict);
149
150 #ifdef FULLDEBUG
151 PDRlegacy::print_info(pdrBlock);
152 #endif
153 }
154
155 // Storage for obstacles and cylinder-like obstacles
156 DynamicList<PDRobstacle> obstacles, cylinders;
157
158 // Read in obstacles
159 const scalar volObstacles =
160 (
162 ? PDRobstacle::legacyReadFiles
163 (
165 pdrBlock.bounds(),
166 obstacles,
167 cylinders
168 )
169 : PDRobstacle::readFiles
170 (
171 pars.obsfile_dir, pars.obsfile_names,
172 pdrBlock.bounds(),
173 obstacles,
174 cylinders
175 )
176 );
177
178
179 PDRobstacle::generateVtk(casepath/"VTK", obstacles, cylinders);
180
181 if (args.dryRun())
182 {
183 Info<< nl
184 << "dry-run: stopping after reading/writing obstacles" << nl
185 << "\nEnd\n" << nl;
186 return 0;
187 }
188
189
190 // Bookkeeping of the ranges within the obstacle list
191
192 // Original blockage at the start
193 const labelRange origBlocks(0, obstacles.size());
194
195 // Intersection blockage
196 labelRange interBlocks(origBlocks.after(), 0);
197
198 scalar volSubtract = 0;
199
200 // Do binary intersections between blocks and cylinders (or diag-beam)
201 // by creating -ve blocks at the overlap
202
203 labelRange int1Blocks(origBlocks.after(), 0);
204
205 if (pars.overlaps % 2 > 0)
206 {
207 Info<< " block/cylinder intersections" << endl;
208
209 label nblocked = obstacles.size();
210
211 volSubtract += block_cylinder_overlap(obstacles, origBlocks, cylinders);
212
213 nblocked = (obstacles.size() - nblocked);
214
215 interBlocks += nblocked;
216 int1Blocks += nblocked;
217 }
218
219 // Do binary intersections between blocks
220 // by creating -ve blocks at the overlap
221
222 labelRange int2Blocks(int1Blocks.after(), 0);
223 if (pars.overlaps % 4 > 1)
224 {
225 Info<< " block/block intersections" << endl;
226
227 label nblocked = obstacles.size();
228
229 volSubtract += block_overlap(obstacles, origBlocks, 1.0);
230
231 nblocked = (obstacles.size() - nblocked);
232
233 interBlocks += nblocked;
234 int2Blocks += nblocked;
235 }
236
237 // Correct for triple intersections
238 // by looking for overlaps between the -ve blocks just created
239
240 labelRange int3Blocks(int2Blocks.after(), 0);
241 if (pars.overlaps % 8 > 3)
242 {
243 Info<< " triple intersections" << endl;
244
245 label nblocked = obstacles.size();
246
247 volSubtract += block_overlap(obstacles, interBlocks, 1.0/3.0);
248
249 nblocked = (obstacles.size() - nblocked);
250
251 interBlocks += nblocked;
252 int3Blocks += nblocked;
253 }
254
255
256 // The field arrays, in one structure pass around easily
257 PDRarrays arr(pdrBlock);
258
259 Info<< "Apply blockage" << endl;
260
261 // Create blockage and count arrays by working through
262 // real and extra blocks and cylinders
263
264 // User-defined negative blocks. Use "sign" to distinguish
265 if (origBlocks.size())
266 {
267 Info<< " negative blocks: " << origBlocks.size() << nl;
268
269 for (const PDRobstacle& obs : obstacles.slice(origBlocks))
270 {
271 arr.addBlockage(obs, patches, -1);
272 }
273 }
274
275 // Do the intersection blocks positive and negative
276 // These are done first so that negative area blockage cancels positive
277
278 if (interBlocks.size())
279 {
280 Info<< " blocks " << interBlocks.size() << nl;
281
282 for (const PDRobstacle& obs : obstacles.slice(interBlocks))
283 {
284 arr.addBlockage(obs, patches, 0);
285 }
286 }
287
288 // The positive real bocks
289 if (origBlocks.size())
290 {
291 Info<< " positive blocks: " << origBlocks.size() << nl;
292
293 for (const PDRobstacle& obs : obstacles.slice(origBlocks))
294 {
295 arr.addBlockage(obs, patches, 1);
296 }
297 }
298
299 // The cylinders
300 if (cylinders.size())
301 {
302 Info<< " cylinders: " << cylinders.size() << nl;
303
304 for (const PDRobstacle& obs : cylinders)
305 {
306 arr.addCylinder(obs);
307 }
308 }
309
310 // Calculation of the fields of drag, turbulence
311 // generation and combustion enhancement
312
313 arr.blockageSummary();
314
315 // Mapping of OpenFOAM cells/faces to i-j-k indices
316 PDRmeshArrays meshIdx;
318
319 meshIdx.read(runTime, pdrBlock);
320
321 PDRarrays::calculateAndWrite(arr, meshIdx, casepath, patches);
322
323 Info<< nl
324 << setw(6) << origBlocks.size() << " blocks and "
325 << cylinders.size() << " cylinders/diagonal blocks" << nl;
326
327 Info<< setw(6) << int2Blocks.size()
328 << " intersections amongst blocks" << nl;
329
330 Info<< setw(6) << int1Blocks.size()
331 << " intersections between blocks and cyl/beams" << nl;
332
333 Info<< setw(6) << int1Blocks.size()
334 << "/3 triple intersections" << nl;
335
336 Info<< "Volume of obstacles read in: " << volObstacles
337 << ", volume of intersections: " << volSubtract << nl;
338
339 Info<< nl << "After corrections:" << nl;
340 arr.blockageSummary();
341
342 Info<< nl << "\nEnd\n" << endl;
343
344 return 0;
345}
346
347
348// ************************************************************************* //
Istream and Ostream manipulators taking arguments.
Preparation of fields for PDRFoam.
scalar block_overlap(DynamicList< PDRobstacle > &blocks, const labelRange &range, const scalar multiplier=1.0)
Calculate block/block overlaps.
scalar block_cylinder_overlap(DynamicList< PDRobstacle > &blocks, const labelRange &range, const UList< PDRobstacle > &cylinders)
Calculate block/cylinder overlaps.
A 1D vector of objects of type <T> that resizes itself as necessary to accept the new objects.
Definition: DynamicList.H:72
IOdictionary is derived from dictionary and IOobject to give the dictionary automatic IO functionalit...
Definition: IOdictionary.H:57
Defines the attributes of an object for which implicit objectRegistry management is supported,...
Definition: IOobject.H:170
Work array definitions for PDR fields.
Definition: PDRarrays.H:64
A single block x-y-z rectilinear mesh addressable as i,j,k with simplified creation....
Definition: PDRblock.H:156
bool read(const dictionary &dict)
Read dictionary.
Definition: PDRblock.C:564
OpenFOAM/PDRblock addressing information.
Definition: PDRmeshArrays.H:66
void read(const Time &runTime, const PDRblock &pdrBlock)
Read OpenFOAM mesh and determine i-j-k indices for faces/cells.
static scalar gridPointRelTol
Relative tolerance when matching grid points. Default = 0.02.
Definition: PDRmeshArrays.H:70
Obstacle definitions for PDR.
Definition: PDRobstacle.H:75
wordList obsfile_names
Definition: PDRparams.H:62
bool legacyObsSpec
Definition: PDRparams.H:74
void read(const dictionary &dict)
Read program parameters from dictionary.
scalar gridPointTol
Definition: PDRparams.H:99
int overlaps
Flag to control which overlap calculations are performed.
Definition: PDRparams.H:97
fileName obsfile_dir
Definition: PDRparams.H:61
bool legacyMeshSpec
Definition: PDRparams.H:73
predefined
Patch predefines.
Definition: PDRpatchDef.H:59
SubList< T > slice(const label pos, label len=-1)
Return SubList slice (non-const access) - no range checking.
Definition: SubList.H:165
void size(const label n)
Older name for setAddressableSize.
Definition: UList.H:114
int dryRun() const noexcept
Return the dry-run flag.
Definition: argListI.H:116
bool found(const word &optName) const
Return true if the named option is found.
Definition: argListI.H:178
bool readIfPresent(const word &optName, T &val) const
Read a value from the named option if present.
Definition: argListI.H:323
A class for handling file names.
Definition: fileName.H:76
A range or interval of labels defined by a start and a size.
Definition: labelRange.H:58
A class for handling words, derived from Foam::string.
Definition: word.H:68
const polyBoundaryMesh & patches
engineTime & runTime
const word dictName("faMeshDefinition")
Namespace for OpenFOAM.
messageStream Info
Information stream (stdout output on master, null elsewhere)
Omanip< int > setw(const int i)
Definition: IOmanip.H:199
Ostream & endl(Ostream &os)
Add newline and flush stream.
Definition: Ostream.H:372
Foam::PDRparams pars
Globals for program parameters (ugly hack)
constexpr char nl
The newline '\n' character (0x0a)
Definition: Ostream.H:53
IOobject dictIO
Foam::argList args(argc, argv)