56 Info<<
"NO MATCH for source face " << srcFacei <<
endl;
69 const face& srcF = src[srcFacei];
71 for (
const label pointi : srcF)
73 const point&
p = srcPoints[pointi];
74 os <<
"v " <<
p.x() <<
" " <<
p.y() <<
" " <<
p.z() <<
nl;
78 os << faceStr.c_str() <<
" " << (np - srcF.size() + 1) <<
nl;
81 for (
const label tgtFacei : tgtFaceCandidates)
83 const face& tgtF = tgt[tgtFacei];
86 const point&
p = tgtPoints[tgtF[pointi]];
87 os <<
"v " <<
p.x() <<
" " <<
p.y() <<
" " <<
p.z() <<
nl;
91 os <<
"l " << np-1 <<
" " << np <<
nl;
94 os <<
"l " << (np - tgtF.size() + 1) <<
" " << np <<
nl;
99 OFstream
os(
"no_match_" +
Foam::name(srcFacei) +
"_bb.obj");
104 os <<
"v " <<
p.x() <<
" " <<
p.y() <<
" " <<
p.z() <<
endl;
124 const label srcFacei,
125 const label tgtFacei,
126 DynamicList<label>& srcAddr,
127 DynamicList<scalar>& srcWght,
128 DynamicList<vector>& srcCtr,
129 DynamicList<label>& tgtAddr,
130 DynamicList<scalar>& tgtWght
133 addProfiling(ami,
"faceAreaWeightAMI2D::calcInterArea");
136 if (!isCandidate(srcFacei, tgtFacei))
141 const auto& srcPatch = this->srcPatch();
142 const auto& tgtPatch = this->tgtPatch();
147 const auto& srcTris = srcTris_[srcFacei];
148 const auto& tgtTris = tgtTris_[tgtFacei];
150 const auto& srcFaceNormals = srcPatch.
faceNormals();
157 for (
const auto& tris : srcTris)
159 const vector& origin = srcPoints[tris[0]];
160 const vector p10(srcPoints[tris[1]] - origin);
161 const vector p20(srcPoints[tris[2]] - origin);
162 const vector axis1(p10/(
mag(p10) + ROOTVSMALL));
163 const vector axis2(srcFaceNormals[srcFacei]^axis1);
172 for (
const auto& trit : tgtTris)
177 tgtPoints[trit[0]] - origin,
178 tgtPoints[trit[2]] - origin,
179 tgtPoints[trit[1]] - origin,
187 if (t.snapClosePoints(
s) == 3)
194 s.interArea(t,
c, da);
198 centroid += da*(origin +
c.x()*axis1 +
c.y()*axis2);
206 centroid /=
area + ROOTVSMALL;
209 srcWght.append(
area);
210 srcCtr.append(centroid);
212 tgtAddr.append(srcFacei);
213 tgtWght.append(
area);
220 const AABBTree<face>&
tree,
221 const List<boundBox>& tgtFaceBbs,
222 const boundBox& srcFaceBb
227 const auto& treeBb =
tree.boundBoxes();
228 const auto& treeAddr =
tree.addressing();
232 const auto& tbb = treeBb[boxi];
234 if (srcFaceBb.overlaps(tbb))
236 const auto& boxAddr = treeAddr[boxi];
238 for (
const auto& tgtFacei : boxAddr)
240 if (srcFaceBb.overlaps(tgtFaceBbs[tgtFacei]))
242 faceIds.insert(tgtFacei);
248 return faceIds.toc();
257 const bool reverseTarget
267 const bool requireMatch,
268 const bool reverseTarget,
269 const scalar lowWeightCorrection,
271 const bool restartUncoveredSourceFace
313 const auto& src = this->srcPatch();
314 const auto& tgt = this->tgtPatch();
316 bool validSize =
true;
323 else if (!tgt.size())
326 << src.size() <<
" source faces but no target faces" <<
endl;
331 srcCentroids_.setSize(srcAddress_.size());
334 List<DynamicList<label>> tgtAddr(tgt.size());
335 List<DynamicList<scalar>> tgtWght(tgt.size());
343 const bool equalBinSize =
true;
344 const label maxLevel = 10;
345 const label minBinSize = 4;
355 const auto& tgtPoints = tgt.points();
356 List<boundBox> tgtFaceBbs(tgt.size());
359 tgtFaceBbs[facei] = boundBox(tgtPoints, tgt[facei],
false);
362 DynamicList<label> nonOverlapFaces;
364 const auto& srcPoints = src.points();
368 const face& srcFace = src[srcFacei];
370 treeBoundBox srcFaceBb(srcPoints, srcFace);
375 overlappingTgtFaces(
tree, tgtFaceBbs, srcFaceBb)
378 DynamicList<label> srcAddr(tgtFaces.size());
379 DynamicList<scalar> srcWght(tgtFaces.size());
380 DynamicList<point> srcCtr(tgtFaces.size());
382 for (
const label tgtFacei : tgtFaces)
396 if (mustMatchFaces() && srcAddr.empty())
398 if (
debug) writeNoMatch(srcFacei, tgtFaces, srcFaceBb);
405 srcAddress_[srcFacei].transfer(srcAddr);
406 srcWeights_[srcFacei].transfer(srcWght);
407 srcCentroids_[srcFacei].transfer(srcCtr);
410 srcNonOverlap_.transfer(nonOverlapFaces);
412 if (
debug && !srcNonOverlap_.empty())
414 Pout<<
" AMI: " << srcNonOverlap_.size()
415 <<
" non-overlap faces identified" 424 tgtAddress_[i].transfer(tgtAddr[i]);
425 tgtWeights_[i].transfer(tgtWght[i]);
436 const globalIndex globalSrcFaces(srcPatch0.size(), comm_);
437 const globalIndex globalTgtFaces(tgtPatch0.size(), comm_);
439 for (
labelList& addressing : srcAddress_)
441 for (label& addr : addressing)
443 addr = extendedTgtFaceIDs_[addr];
447 for (
labelList& addressing : tgtAddress_)
449 globalSrcFaces.inplaceToGlobal(myRank, addressing);
460 extendedTgtMapPtr_->constructMap(),
462 extendedTgtMapPtr_->subMap(),
466 ListOps::appendEqOp<label>(),
477 extendedTgtMapPtr_->constructMap(),
479 extendedTgtMapPtr_->subMap(),
483 ListOps::appendEqOp<scalar>(),
490 extendedTgtMapPtr_->reverseDistribute(tgtPatch0.size(), tgtMagSf_);
493 List<Map<label>> cMapSrc;
506 List<Map<label>> cMapTgt;
521 normaliseWeights(requireMatch_,
true);
523 nonConformalCorrection();
List< scalar > scalarList
List of scalar.
void writeNoMatch(const label srcFacei, const labelList &tgtFaceCandidates, const boundBox &srcFaceBb) const
Helper function to write non-matched source faces to the set of candidate faces.
virtual bool calculate(const primitivePatch &srcPatch, const primitivePatch &tgtPatch, const autoPtr< searchableSurface > &surfPtr=nullptr)
Update addressing, weights and (optional) centroids.
A face is a list of labels corresponding to mesh vertices.
dimensioned< typename typeOfMag< Type >::type > mag(const dimensioned< Type > &dt)
A list of keyword definitions, which are a keyword followed by a number of values (eg...
void append(const T &val)
Append an element at the end of the list.
Output to file stream as an OSstream, normally using std::ofstream for the actual output...
constexpr char nl
The newline '\n' character (0x0a)
Vector2D< scalar > vector2D
A 2D vector of scalars obtained from the generic Vector2D.
dimensionedScalar sqrt(const dimensionedScalar &ds)
Ostream & endl(Ostream &os)
Add newline and flush stream.
#define addProfiling(Name,...)
Define profiling trigger with specified name and description string. The description is generated by ...
A bounding box defined in terms of min/max extrema points.
static int & msgType() noexcept
Message tag of standard messages.
static int myProcNo(const label communicator=worldComm)
Rank of this process in the communicator (starting from masterNo()). Can be negative if the process i...
virtual void write(Ostream &os) const
Write.
Macros for easy insertion into run-time selection tables.
#define forAll(list, i)
Loop across all elements in list.
virtual void write(Ostream &os) const
Write.
HashSet< label, Hash< label > > labelHashSet
A HashSet of labels, uses label hasher.
const primitivePatch & tgtPatch() const
Return const access to the target patch.
const Field< point_type > & faceNormals() const
Return face unit normals for patch.
A list of faces which address into the list of points.
vectorField pointField
pointField is a vectorField.
word name(const expressions::valueTypeCode typeCode)
A word representation of a valueTypeCode. Empty for expressions::valueTypeCode::INVALID.
const wordList area
Standard area field types (scalar, vector, tensor, etc)
Face area weighted Arbitrary Mesh Interface (AMI) method that performs the intersection of src and tg...
Tree tree(triangles.begin(), triangles.end())
const Field< point_type > & points() const noexcept
Return reference to global points.
Ostream & writeEntryIfDifferent(const word &key, const T &value1, const T &value2)
Write a keyword/value entry only when the two values differ.
An Ostream is an abstract base class for all output systems (streams, files, token lists...
A Vector of values with scalar precision, where scalar is float/double depending on the compilation f...
int debug
Static debugging option.
OBJstream os(runTime.globalPath()/outputName)
labelList overlappingTgtFaces(const AABBTree< face > &tree, const List< boundBox > &tgtFaceBbs, const boundBox &srcFaceBb) const
Return the set of tgt face IDs that overlap the src face bb.
defineTypeNameAndDebug(combustionModel, 0)
PrimitivePatch< SubList< face >, const pointField & > primitivePatch
A PrimitivePatch with a SubList addressing for the faces, const reference for the point field...
virtual bool calculate(const primitivePatch &srcPatch, const primitivePatch &tgtPatch, const autoPtr< searchableSurface > &surfPtr=nullptr)
Update addressing, weights and (optional) centroids.
vector point
Point is a vector.
#define WarningInFunction
Report a warning using Foam::Warning.
faceAreaWeightAMI2D(const dictionary &dict, const bool reverseTarget=false)
Construct from dictionary.
Type gAverage(const FieldField< Field, Type > &f)
tmp< pointField > points() const
Corner points in an order corresponding to a 'hex' cell.
Base class for Arbitrary Mesh Interface (AMI) methods.
const dimensionedScalar c
Speed of light in a vacuum.
void storeInterArea(const label srcFacei, const label tgtFacei, DynamicList< label > &srcAddr, DynamicList< scalar > &srcWght, DynamicList< vector > &srcCtr, DynamicList< label > &tgtAddr, DynamicList< scalar > &tgtWght) const
Calculate and store the area of intersection between source and target faces.
static scalar relTol
Relative tolerance.
"nonBlocking" (immediate) : (MPI_Isend, MPI_Irecv)
messageStream Info
Information stream (stdout output on master, null elsewhere)
Pointer management similar to std::unique_ptr, with some additional methods and type checking...
List< label > labelList
A List of labels.
gmvFile<< "tracers "<< particles.size()<< nl;for(const passiveParticle &p :particles){ gmvFile<< p.position().x()<< " ";}gmvFile<< nl;for(const passiveParticle &p :particles){ gmvFile<< p.position().y()<< " ";}gmvFile<< nl;for(const passiveParticle &p :particles){ gmvFile<< p.position().z()<< " ";}gmvFile<< nl;forAll(lagrangianScalarNames, i){ word name=lagrangianScalarNames[i];IOField< scalar > s(IOobject(name, runTime.timeName(), cloud::prefix, mesh, IOobject::MUST_READ, IOobject::NO_WRITE))
void component(FieldField< Field, typename FieldField< Field, Type >::cmptType > &sf, const FieldField< Field, Type > &f, const direction d)
static const List< T > & null() noexcept
Return a null List (reference to a nullObject). Behaves like an empty List.
const primitivePatch & srcPatch() const
Return const access to the source patch.
prefixOSstream Pout
OSstream wrapped stdout (std::cout) with parallel prefix.
static void distribute(const UPstream::commsTypes commsType, const List< labelPair > &schedule, const label constructSize, const labelListList &subMap, const bool subHasFlip, const labelListList &constructMap, const bool constructHasFlip, List< T > &field, const T &nullValue, const CombineOp &cop, const NegateOp &negOp, const int tag=UPstream::msgType(), const label comm=UPstream::worldComm)
Distribute combine data with specified combine operation and negate operator (for flips)...
addToRunTimeSelectionTable(functionObject, pointHistory, dictionary)
static constexpr const zero Zero
Global zero (0)