diff --git a/src/functionObjects/field/Make/files b/src/functionObjects/field/Make/files index 290a84dfe3..c285367b66 100644 --- a/src/functionObjects/field/Make/files +++ b/src/functionObjects/field/Make/files @@ -20,7 +20,6 @@ fieldValues/fieldValue/fieldValue.C fieldValues/fieldValue/fieldValueNew.C fieldValues/volFieldValue/volFieldValue.C fieldValues/surfaceFieldValue/surfaceFieldValue.C -fieldValues/multiFieldValue/multiFieldValue.C heatTransferCoeff/heatTransferCoeff.C heatTransferCoeff/heatTransferCoeffModels/heatTransferCoeffModel/heatTransferCoeffModel.C @@ -31,6 +30,8 @@ heatTransferCoeff/heatTransferCoeffModels/ReynoldsAnalogy/ReynoldsAnalogy.C limitFields/limitFields.C +multiFieldValue/multiFieldValue.C + nearWallFields/nearWallFields.C nearWallFields/findCellParticle.C nearWallFields/findCellParticleCloud.C diff --git a/src/functionObjects/field/fieldValues/multiFieldValue/multiFieldValue.C b/src/functionObjects/field/multiFieldValue/multiFieldValue.C similarity index 56% rename from src/functionObjects/field/fieldValues/multiFieldValue/multiFieldValue.C rename to src/functionObjects/field/multiFieldValue/multiFieldValue.C index 251a9a47da..45cf5bb8d1 100644 --- a/src/functionObjects/field/fieldValues/multiFieldValue/multiFieldValue.C +++ b/src/functionObjects/field/multiFieldValue/multiFieldValue.C @@ -6,7 +6,7 @@ \\/ M anipulation | ------------------------------------------------------------------------------- Copyright (C) 2012-2016 OpenFOAM Foundation - Copyright (C) 2015-2021 OpenCFD Ltd. + Copyright (C) 2015-2022 OpenCFD Ltd. ------------------------------------------------------------------------------- License This file is part of OpenFOAM. @@ -63,48 +63,36 @@ Foam::functionObjects::fieldValues::multiFieldValue::operationTypeNames_ void Foam::functionObjects::fieldValues::multiFieldValue::writeFileHeader ( + const wordList& foNames, + const List& entries, + const List& types, Ostream& os ) const { - const wordList& fields0 = functions_[0].fields(); + const word groupPrefix("Group"); - DynamicList commonFields(fields0.size()); - - for (const word& fieldName : fields0) + forAll(entries, i) { - bool common = true; + writeCommented(os, groupPrefix + Foam::name(i)); + os << nl; - for (label functioni=1; functioni < functions_.size(); ++functioni) + forAll(entries[i], functioni) { - if (!functions_[functioni].fields().found(fieldName)) - { - common = false; - break; - } + writeCommented + ( + os, + " - " + foNames[functioni] + ":" + entries[i][functioni] + ); + os << nl; } - - if (common) - { - commonFields.append(fieldName); - } - } - - forAll(functions_, functioni) - { - writeHeaderValue - ( - os, - "Source" + Foam::name(functioni), - functions_[functioni].name() - ); } writeHeaderValue(os, "Operation", operationTypeNames_[operation_]); writeCommented(os, "Time"); - for (const word& fieldName : commonFields) + forAll(entries, entryi) { - os << tab << fieldName; + writeTabbed(os, groupPrefix + Foam::name(entryi)); } os << endl; @@ -125,10 +113,7 @@ Foam::functionObjects::fieldValues::multiFieldValue::multiFieldValue operation_(opSubtract), functions_() { - if (read(dict)) - { - writeFileHeader(file()); - } + read(dict); } @@ -139,52 +124,73 @@ bool Foam::functionObjects::fieldValues::multiFieldValue::read const dictionary& dict ) { - if (stateFunctionObject::read(dict) && writeFile::read(dict)) + if (!stateFunctionObject::read(dict) || !writeFile::read(dict)) { - const dictionary& functionsDict = dict.subDict("functions"); - functions_.resize(functionsDict.size()); - - if (functions_.empty()) - { - WarningInFunction - << "No functions specified" - << endl; - return false; - } - - label functioni = 0; - for (const entry& dEntry : functionsDict) - { - if (!dEntry.isDict()) - { - FatalIOErrorInFunction(dict) - << "Functions must be specified in dictionary format" - << exit(FatalIOError); - } - - const dictionary& localDict = dEntry.dict(); - - functions_.set - ( - functioni, - fieldValue::New - ( - IOobject::scopedName(name(), localDict.dictName()), - time(), - localDict, - false - ) - ); - - ++functioni; - } - - operation_ = operationTypeNames_.get("operation", dict); - - return true; + return false; } - return false; + operation_ = operationTypeNames_.get("operation", dict); + + const dictionary& functionsDict = dict.subDict("functions"); + functions_.resize(functionsDict.size()); + + if (functions_.empty()) + { + WarningInFunction + << "No functions specified" + << endl; + return false; + } + + resultFields_.resize(functions_.size()); + + label functioni = 0; + for (const entry& dEntry : functionsDict) + { + if (!dEntry.isDict()) + { + FatalIOErrorInFunction(dict) + << "Functions must be specified in dictionary format" + << exit(FatalIOError); + } + + const dictionary& localDict = dEntry.dict(); + + functions_.set + ( + functioni, + functionObject::New + ( + IOobject::scopedName(name(), localDict.dictName()), + time(), + localDict + ).ptr() + ); + + // Deactivate logging for child function objects + //functions_[functioni].log = false; + + // Get result field names; not specified implies all + resultFields_[functioni] = + localDict.getOrDefault("resultFields", wordList()); + + Info<< type() << ' ' << name() << ':' << nl; + if (resultFields_[functioni].size()) + { + Info<< " " << functions_[functioni].name() + << " " << resultFields_[functioni]; + } + else + { + Info<< " " << functions_[functioni].name() + << " - using all available entries"; + } + Info<< nl << endl; + + ++functioni; + } + + return true; } @@ -201,19 +207,25 @@ bool Foam::functionObjects::fieldValues::multiFieldValue::write() wordList entries0; label nEntries = -1; - wordList names(nFunction); + wordList foNames(nFunction); List entries; List types; forAll(functions_, functioni) { auto& f = functions_[functioni]; - names[functioni] = f.name(); + foNames[functioni] = f.name(); - // Note: results are not available until the call to write() + // Note: replicating functionObjectList execute() and write() + // - results may be written on either + f.execute(); f.write(); - const wordList e(objectResultEntries(f.name())); + wordList e = resultFields_[functioni]; + if (e.empty()) + { + e = objectResultEntries(f.name()); + } if (functioni == 0) { @@ -237,54 +249,72 @@ bool Foam::functionObjects::fieldValues::multiFieldValue::write() << "Inconsistent number of result entries" << nl << " " << f0Name << " entries:" << entries0 << nl << " " << f.name() << " entries:" << e - << abort(FatalError); + << exit(FatalError); } forAll(e, entryi) { entries[entryi][functioni] = e[entryi]; types[entryi][functioni] = objectResultType(f.name(), e[entryi]); + + if (types[entryi][functioni] == word::null) + { + FatalErrorInFunction + << "Unable to find function object result" << nl + << " function object : " << f.name() << nl + << " result name : " << e[entryi] << nl + << " available results : " + << objectResultEntries(f.name()) + << exit(FatalError); + } } } + if (!writtenHeader_) + { + writeFileHeader(foNames, entries, types, file()); + writtenHeader_ = true; + } + writeCurrentTime(file()); - forAll(entries, entryi) + forAll(entries, i) { - const wordList& entriesi = entries[entryi]; - const word& t0 = types[entryi][0]; - const wordList& typesi = types[entryi]; - forAll(typesi, functioni) - { - const word& t = typesi[functioni]; + const wordList& entryi = entries[i]; + const word& expectedType = types[i][0]; + const wordList& foTypes = types[i]; - if (t != t0) + forAll(foTypes, functioni) + { + const word& foType = foTypes[functioni]; + + if (foType != expectedType) { FatalErrorInFunction << "Inconsistent function result types" << nl << " " << functions_[0].name() - << " result type:" << t0 << nl + << " result type:" << expectedType << nl << " " << functions_[functioni].name() - << " result type:" << typesi[functioni] - << abort(FatalError); + << " result type:" << foType + << exit(FatalError); } } const bool ok ( - applyOperation(t0, names, entriesi) - || applyOperation(t0, names, entriesi) - || applyOperation(t0, names, entriesi) - || applyOperation(t0, names, entriesi) - || applyOperation(t0, names, entriesi) + applyOperation(expectedType, foNames, entryi) + || applyOperation(expectedType, foNames, entryi) + || applyOperation(expectedType, foNames, entryi) + || applyOperation(expectedType, foNames, entryi) + || applyOperation(expectedType, foNames, entryi) ); if (!ok) { Log << "Operation not applied between functions:" << nl - << flatOutput(names, FlatOutput::BareComma{}) << nl + << flatOutput(foNames, FlatOutput::BareComma{}) << nl << "with result names:" << nl - << flatOutput(entriesi, FlatOutput::BareComma{}) + << flatOutput(entryi, FlatOutput::BareComma{}) << endl; } } diff --git a/src/functionObjects/field/fieldValues/multiFieldValue/multiFieldValue.H b/src/functionObjects/field/multiFieldValue/multiFieldValue.H similarity index 77% rename from src/functionObjects/field/fieldValues/multiFieldValue/multiFieldValue.H rename to src/functionObjects/field/multiFieldValue/multiFieldValue.H index d6b73499eb..02a939ff12 100644 --- a/src/functionObjects/field/fieldValues/multiFieldValue/multiFieldValue.H +++ b/src/functionObjects/field/multiFieldValue/multiFieldValue.H @@ -5,7 +5,7 @@ \\ / A nd | www.openfoam.com \\/ M anipulation | ------------------------------------------------------------------------------- - Copyright (C) 2021 OpenCFD Ltd. + Copyright (C) 2021-2022 OpenCFD Ltd. ------------------------------------------------------------------------------- License This file is part of OpenFOAM. @@ -30,10 +30,9 @@ Group grpFieldFunctionObjects Description - Computes a selected operation between multiple \c fieldValue function - objects. + Computes a selected operation between multiple function objects. - The operation is applied to all results of each \c fieldValue object. + The operation is applied to all results of each object. Note Each object must generate the same number and type of results. @@ -43,11 +42,9 @@ Usage \verbatim multiFieldValue1 { - // Mandatory entries (unmodifiable) - type multiFieldValue; - libs (fieldFunctionObjects); - - // Mandatory entries (runtime modifiable) + // Mandatory entries + type multiFieldValue; + libs (fieldFunctionObjects); operation average; // List of fieldValue function objects as dictionaries @@ -56,10 +53,14 @@ Usage region1 { ... + // Optional + resultFields (field1 field2); } region2 { ... + // Optional + resultFields (field1 field2); } ... @@ -67,41 +68,41 @@ Usage regionN { ... + // Optional + resultFields (field1 field2); } } - // Optional (inherited) entries + // Inherited entries ... } \endverbatim where the entries mean: \table - Property | Description | Type | Req'd | Dflt - type | Type name: multiFieldValue | word | yes | - - libs | Library name: fieldFunctionObjects | word | yes | - - operation | Operation type to apply to values | word | yes | - - functions | List of fieldValue function objects | dict | yes | - + Property | Description | Type | Reqd | Deflt + type | Type name: multiFieldValue | word | yes | - + libs | Library name: fieldFunctionObjects | word | yes | - + operation | Operation type to apply to values | word | yes | - + functions | List of function objects | dict | yes | - \endtable Options for the \c operation entry: \plaintable - add | add - subtract | subtract - min | minimum - max | maximum - average | average + sum | Sum of values + add | Add values (same as sum) + subtract | Subtract values from first entry + min | Minimum value + max | Maximum value + average | Average value \endplaintable + The \c resultFields entry can be used to set the name of the function object + result fields to process. If omitted, all available values are employed. + The inherited entries are elaborated in: - - \link fieldValue.H \endlink - - Usage by the \c postProcess utility is not available. - -See also - - Foam::functionObject - - Foam::functionObjects::fieldValue - - ExtendedCodeGuide::functionObjects::field::multiFieldValue + - \link stateFunctionObject.H \endlink + - \link writeFile.H \endlink SourceFiles multiFieldValue.C @@ -114,7 +115,6 @@ SourceFiles #include "stateFunctionObject.H" #include "writeFile.H" -#include "fieldValue.H" #include "Enum.H" // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // @@ -161,8 +161,11 @@ private: //- Operation to apply to values operationType operation_; - //- List of fieldValue function objects - PtrList functions_; + //- List of function objects + PtrList functions_; + + //- List of result fields per function object + List resultFields_; // Private Member Functions @@ -183,7 +186,13 @@ protected: // Protected Member Functions //- Output file header information - virtual void writeFileHeader(Ostream& os) const; + virtual void writeFileHeader + ( + const wordList& foNames, + const List& entries, + const List& types, + Ostream& os + ) const; public: diff --git a/src/functionObjects/field/fieldValues/multiFieldValue/multiFieldValueTemplates.C b/src/functionObjects/field/multiFieldValue/multiFieldValueTemplates.C similarity index 94% rename from src/functionObjects/field/fieldValues/multiFieldValue/multiFieldValueTemplates.C rename to src/functionObjects/field/multiFieldValue/multiFieldValueTemplates.C index 714cb1c48b..5f6c99c084 100644 --- a/src/functionObjects/field/fieldValues/multiFieldValue/multiFieldValueTemplates.C +++ b/src/functionObjects/field/multiFieldValue/multiFieldValueTemplates.C @@ -6,7 +6,7 @@ \\/ M anipulation | ------------------------------------------------------------------------------- Copyright (C) 2012-2016 OpenFOAM Foundation - Copyright (C) 2015-2021 OpenCFD Ltd. + Copyright (C) 2015-2022 OpenCFD Ltd. ------------------------------------------------------------------------------- License This file is part of OpenFOAM. @@ -34,7 +34,7 @@ template bool Foam::functionObjects::fieldValues::multiFieldValue::applyOperation ( const word& resultType, - const wordList& names, + const wordList& foNames, const wordList& entryNames ) { @@ -45,10 +45,10 @@ bool Foam::functionObjects::fieldValues::multiFieldValue::applyOperation Type result = Zero; - Field values(names.size()); + Field values(foNames.size()); forAll(values, i) { - values[i] = this->getObjectResult(names[i], entryNames[i]); + values[i] = this->getObjectResult(foNames[i], entryNames[i]); } const word& opName = operationTypeNames_[operation_]; diff --git a/src/lagrangian/intermediate/parcels/include/makeParcelCloudFunctionObjects.H b/src/lagrangian/intermediate/parcels/include/makeParcelCloudFunctionObjects.H index e11442604b..f95d5d0ef0 100644 --- a/src/lagrangian/intermediate/parcels/include/makeParcelCloudFunctionObjects.H +++ b/src/lagrangian/intermediate/parcels/include/makeParcelCloudFunctionObjects.H @@ -6,7 +6,7 @@ \\/ M anipulation | ------------------------------------------------------------------------------- Copyright (C) 2011-2018 OpenFOAM Foundation - Copyright (C) 2020-2021 OpenCFD Ltd. + Copyright (C) 2020-2022 OpenCFD Ltd. ------------------------------------------------------------------------------- License This file is part of OpenFOAM. @@ -37,6 +37,7 @@ License #include "ParticleErosion.H" #include "ParticleTracks.H" #include "ParticleTrap.H" +#include "ParticleZoneInfo.H" #include "PatchCollisionDensity.H" #include "PatchInteractionFields.H" #include "PatchPostProcessing.H" @@ -57,6 +58,7 @@ License makeCloudFunctionObjectType(ParticleErosion, CloudType); \ makeCloudFunctionObjectType(ParticleTracks, CloudType); \ makeCloudFunctionObjectType(ParticleTrap, CloudType); \ + makeCloudFunctionObjectType(ParticleZoneInfo, CloudType); \ makeCloudFunctionObjectType(PatchCollisionDensity, CloudType); \ makeCloudFunctionObjectType(PatchInteractionFields, CloudType); \ makeCloudFunctionObjectType(PatchPostProcessing, CloudType); \ diff --git a/src/lagrangian/intermediate/parcels/include/makeReactingParcelCloudFunctionObjects.H b/src/lagrangian/intermediate/parcels/include/makeReactingParcelCloudFunctionObjects.H index 61e0e413cd..16258ff40c 100644 --- a/src/lagrangian/intermediate/parcels/include/makeReactingParcelCloudFunctionObjects.H +++ b/src/lagrangian/intermediate/parcels/include/makeReactingParcelCloudFunctionObjects.H @@ -6,7 +6,7 @@ \\/ M anipulation | ------------------------------------------------------------------------------- Copyright (C) 2011-2018 OpenFOAM Foundation - Copyright (C) 2020-2021 OpenCFD Ltd. + Copyright (C) 2020-2022 OpenCFD Ltd. ------------------------------------------------------------------------------- License This file is part of OpenFOAM. @@ -37,6 +37,7 @@ License #include "ParticleErosion.H" #include "ParticleTracks.H" #include "ParticleTrap.H" +#include "ParticleZoneInfo.H" #include "PatchCollisionDensity.H" #include "PatchInteractionFields.H" #include "PatchPostProcessing.H" @@ -60,6 +61,7 @@ License makeCloudFunctionObjectType(ParticleErosion, CloudType); \ makeCloudFunctionObjectType(ParticleTracks, CloudType); \ makeCloudFunctionObjectType(ParticleTrap, CloudType); \ + makeCloudFunctionObjectType(ParticleZoneInfo, CloudType); \ makeCloudFunctionObjectType(PatchCollisionDensity, CloudType); \ makeCloudFunctionObjectType(PatchInteractionFields, CloudType); \ makeCloudFunctionObjectType(PatchPostProcessing, CloudType); \ diff --git a/src/lagrangian/intermediate/parcels/include/makeThermoParcelCloudFunctionObjects.H b/src/lagrangian/intermediate/parcels/include/makeThermoParcelCloudFunctionObjects.H index 4b641e275b..a703eb8040 100644 --- a/src/lagrangian/intermediate/parcels/include/makeThermoParcelCloudFunctionObjects.H +++ b/src/lagrangian/intermediate/parcels/include/makeThermoParcelCloudFunctionObjects.H @@ -5,7 +5,7 @@ \\ / A nd | www.openfoam.com \\/ M anipulation | ------------------------------------------------------------------------------- - Copyright (C) 2021 OpenCFD Ltd. + Copyright (C) 2021-2022 OpenCFD Ltd. ------------------------------------------------------------------------------- License This file is part of OpenFOAM. @@ -36,6 +36,7 @@ License #include "ParticleErosion.H" #include "ParticleTracks.H" #include "ParticleTrap.H" +#include "ParticleZoneInfo.H" #include "PatchCollisionDensity.H" #include "PatchInteractionFields.H" #include "PatchPostProcessing.H" @@ -58,6 +59,7 @@ License makeCloudFunctionObjectType(ParticleErosion, CloudType); \ makeCloudFunctionObjectType(ParticleTracks, CloudType); \ makeCloudFunctionObjectType(ParticleTrap, CloudType); \ + makeCloudFunctionObjectType(ParticleZoneInfo, CloudType); \ makeCloudFunctionObjectType(PatchCollisionDensity, CloudType); \ makeCloudFunctionObjectType(PatchInteractionFields, CloudType); \ makeCloudFunctionObjectType(PatchPostProcessing, CloudType); \ diff --git a/src/lagrangian/intermediate/submodels/CloudFunctionObjects/ParticleZoneInfo/ParticleZoneInfo.C b/src/lagrangian/intermediate/submodels/CloudFunctionObjects/ParticleZoneInfo/ParticleZoneInfo.C new file mode 100644 index 0000000000..86bacdfb8f --- /dev/null +++ b/src/lagrangian/intermediate/submodels/CloudFunctionObjects/ParticleZoneInfo/ParticleZoneInfo.C @@ -0,0 +1,458 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / O peration | + \\ / A nd | www.openfoam.com + \\/ M anipulation | +------------------------------------------------------------------------------- + Copyright (C) 2022 OpenCFD Ltd. +------------------------------------------------------------------------------- +License + This file is part of OpenFOAM. + + OpenFOAM is free software: you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with OpenFOAM. If not, see . + +\*---------------------------------------------------------------------------*/ + +#include "ParticleZoneInfo.H" +#include "DynamicField.H" + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +namespace Foam +{ +struct particleInfoCombineOp +{ + void operator()(particleInfo& p1, const particleInfo& p2) const + { + // p2 not set + if (p2.origID == -1) + { + return; + } + + // p1 not set - initialise with p2 + if (p1.origID == -1) + { + p1 = p2; + return; + } + + // Set initial values + if (p2.time0 < p1.time0) + { + p1.time0 = p2.time0; + p1.d0 = p2.d0; + p1.mass0 = p2.mass0; + } + + // Accumulate age + p1.age += p2.age; + + // Set latest available values + if (p2.isOlderThan(p1)) + { + p1.position = p2.position; + p1.d = p2.d; + p1.mass = p2.mass; + } + } +}; +} // End namespace Foam + + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +template +Foam::Field getData +( + const Foam::UList& data, + Type Foam::particleInfo::* field +) +{ + Field result(data.size()); + + forAll(data, i) + { + result[i] = data[i].*field; + } + + return result; +} + + +template +Foam::Field getParData +( + const Foam::List>& parData, + Type Foam::particleInfo::* field +) +{ + DynamicField result; + + for (const auto& particles : parData) + { + for (const auto& p : particles) + { + if (p.origID != -1) + { + result.append(p.*field); + } + } + } + + return std::move(result); +} + + +template +void Foam::ParticleZoneInfo::writeWriter +( + const DynamicList& data +) +{ + coordSet coords + ( + "zoneParticles", + "xyz", + getData(data_, &particleInfo::position), + scalarList(data.size(), Zero) + ); + + writerPtr_->open(coords, this->baseTimeDir() / "zoneParticles"); + writerPtr_->beginTime(this->owner().time()); + +#undef writeLocal +#define writeLocal(field) \ + writerPtr_->write(#field, getData(data, &particleInfo::field)); + + writeLocal(origID); + writeLocal(origProc); + writeLocal(time0); + writeLocal(age); + writeLocal(d0); + writeLocal(d); + writeLocal(mass0); + writeLocal(mass); +#undef writeLocal + + writerPtr_->endTime(); + writerPtr_->close(); +} + + +template +void Foam::ParticleZoneInfo::writeWriter +( + const List>& procData +) +{ + vectorField points(getParData(procData, &particleInfo::position)); + + coordSet coords + ( + "zoneParticles", + "xyz", + std::move(points), + scalarList(points.size(), Zero) + ); + + writerPtr_->open(coords, this->baseTimeDir() / "zoneParticles"); + writerPtr_->beginTime(this->owner().time()); + +#undef writeLocal +#define writeLocal(field) \ + writerPtr_->write(#field, getParData(procData, &particleInfo::field)); + + writeLocal(origID); + writeLocal(origProc); + writeLocal(time0); + writeLocal(age); + writeLocal(d0); + writeLocal(d); + writeLocal(mass0); + writeLocal(mass); +#undef writeLocal + + writerPtr_->endTime(); + writerPtr_->close(); +} + + +template +void Foam::ParticleZoneInfo::writeFileHeader(Ostream& os) const +{ + this->writeHeaderValue(os, "cellZone", cellZoneName_); + this->writeHeaderValue(os, "time", this->owner().time().timeOutputValue()); + this->writeHeader(os, ""); + this->writeCommented(os, "origID"); + os << tab << "origProc" + << tab << "(x y z)" + << tab << "time0" + << tab << "age" + << tab << "d0" + << tab << "d" + << tab << "mass0" + << tab << "mass" + << endl; +} + + +template +bool Foam::ParticleZoneInfo::inZone(const label celli) const +{ + return this->owner().mesh().cellZones()[cellZoneId_].whichCell(celli) != -1; +} + + +template +Foam::label Foam::ParticleZoneInfo::getParticleID +( + const particleInfo& p +) const +{ + forAll(data_, i) + { + const auto& d = data_[i]; + if ((d.origProc == p.origProc) && (d.origID == p.origID)) + { + return i; + } + } + + return -1; +} + + +// * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * // + +template +Foam::ParticleZoneInfo::ParticleZoneInfo +( + const dictionary& dict, + CloudType& owner, + const word& modelName +) +: + CloudFunctionObject(dict, owner, modelName, typeName), + functionObjects::writeFile + ( + owner, + this->localPath(), + typeName, + this->coeffDict() + ), + cellZoneName_(this->coeffDict().getWord("cellZone")), + cellZoneId_(-1), + data_(), + movedParticles_(), + maxIDs_(Pstream::nProcs(), Zero), + writerPtr_ + ( + Pstream::master() + ? coordSetWriter::New + ( + this->coeffDict().getWord("writer"), + this->coeffDict().subOrEmptyDict("formatOptions") + ) + : nullptr + ) +{ + const auto& cellZones = owner.mesh().cellZones(); + + cellZoneId_ = cellZones.findZoneID(cellZoneName_); + if (cellZoneId_ == -1) + { + FatalIOErrorInFunction(this->coeffDict()) + << "Unable to find cellZone " << cellZoneName_ + << ". Available cellZones are:" << cellZones.names() + << exit(FatalIOError); + } + + Info<< " Processing cellZone" << cellZoneName_ << " with id " + << cellZoneId_ << endl; +} + + +template +Foam::ParticleZoneInfo::ParticleZoneInfo +( + const ParticleZoneInfo& pzi +) +: + CloudFunctionObject(pzi), + writeFile(pzi), + cellZoneName_(pzi.cellZoneName_), + cellZoneId_(pzi.cellZoneId_), + data_(pzi.data_), + movedParticles_(pzi.movedParticles_), + maxIDs_(Pstream::nProcs()), + writerPtr_(nullptr) +{} + + +// * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * // + +template +void Foam::ParticleZoneInfo::preEvolve +( + const typename parcelType::trackingData& td +) +{} + + +template +void Foam::ParticleZoneInfo::postEvolve +( + const typename parcelType::trackingData& td +) +{ + Info<< this->type() << ":" << nl + << " Cell zone = " << cellZoneName_ << nl + << " Contributions = " + << returnReduce(movedParticles_.size(), sumOp