33 template<
class ParcelType>
39 template<
class ParcelType>
40 template<
class TrackData>
50 rhoc_ = td.rhoInterp().interpolate(this->position(), tetIs);
52 if (rhoc_ < td.cloud().constProps().rhoMin())
58 "void Foam::KinematicParcel<ParcelType>::setCellValues" 64 ) <<
"Limiting observed density in cell " << cellI <<
" to " 65 << td.cloud().constProps().rhoMin() <<
nl <<
endl;
68 rhoc_ = td.cloud().constProps().rhoMin();
71 Uc_ = td.UInterp().interpolate(this->position(), tetIs);
73 muc_ = td.muInterp().interpolate(this->position(), tetIs);
76 Uc_ = td.cloud().dispersion().update
88 template<
class ParcelType>
89 template<
class TrackData>
97 Uc_ += td.cloud().UTrans()[cellI]/massCell(cellI);
101 template<
class ParcelType>
102 template<
class TrackData>
112 const scalar np0 = nParticle_;
113 const scalar mass0 = mass();
116 const scalar Re = this->
Re(U_, d_, rhoc_, muc_);
129 vector dUTrans = vector::zero;
136 this->U_ = calcVelocity(td, dt, cellI, Re, muc_, mass0, Su, dUTrans, Spu);
141 if (td.cloud().solution().coupled())
144 td.cloud().UTrans()[cellI] += np0*dUTrans;
147 td.cloud().UCoeff()[cellI] += np0*Spu;
152 template<
class ParcelType>
153 template<
class TrackData>
167 typedef typename TrackData::cloudType cloudType;
168 typedef typename cloudType::parcelType parcelType;
169 typedef typename cloudType::forceType forceType;
174 const parcelType& p =
static_cast<const parcelType&
>(*this);
175 const forceSuSp Fcp = forces.calcCoupled(p, dt, mass, Re, mu);
176 const forceSuSp Fncp = forces.calcNonCoupled(p, dt, mass, Re, mu);
178 const scalar massEff = forces.massEff(p, mass);
185 const vector abp = (Feff.
Sp()*Uc_ + (Feff.
Su() +
Su))/massEff;
186 const scalar bp = Feff.
Sp()/massEff;
191 td.cloud().UIntegrator().integrate(U_, dt, abp, bp);
196 dUTrans += dt*(Feff.
Sp()*(Ures.
average() - Uc_) - Fcp.
Su());
199 const polyMesh& mesh = td.cloud().pMesh();
209 template<
class ParcelType>
232 template<
class ParcelType>
258 template<
class ParcelType>
259 template<
class TrackData>
263 const scalar trackTime
266 typename TrackData::cloudType::parcelType& p =
267 static_cast<typename TrackData::cloudType::parcelType&
>(*this);
269 td.switchProcessor =
false;
270 td.keepParticle =
true;
272 const polyMesh& mesh = td.cloud().pMesh();
274 const scalarField& cellLengthScale = td.cloud().cellLengthScale();
275 const scalar
maxCo = td.cloud().solution().maxCo();
277 scalar tEnd = (1.0 - p.stepFraction())*trackTime;
278 scalar dtMax = trackTime;
279 if (td.cloud().solution().transient())
284 bool tracking =
true;
285 label nTrackingStalled = 0;
287 while (td.keepParticle && !td.switchProcessor && tEnd > ROOTVSMALL)
292 const point start(p.position());
295 scalar dt =
min(dtMax, tEnd);
298 const label cellI = p.cell();
300 const scalar magU =
mag(U_);
301 if (p.active() && tracking && (magU > ROOTVSMALL))
303 const scalar d = dt*magU;
304 const scalar dCorr =
min(d, maxCo*cellLengthScale[cellI]);
307 *p.trackToFace(p.position() + dCorr*U_/magU, td);
312 scalar newStepFraction = 1.0 - tEnd/trackTime;
318 mag(p.stepFraction() - newStepFraction)
319 < particle::minStepFractionTol
324 if (nTrackingStalled > maxTrackAttempts)
331 nTrackingStalled = 0;
335 p.stepFraction() = newStepFraction;
337 bool calcParcel =
true;
338 if (!tracking && td.cloud().solution().steadyState())
344 if ((dt > ROOTVSMALL) && calcParcel)
347 p.setCellValues(td, dt, cellI);
349 if (td.cloud().solution().cellValueSourceCorrection())
351 p.cellValueSourceCorrection(td, dt, cellI);
354 p.calc(td, dt, cellI);
357 if (p.onBoundary() && td.keepParticle)
359 if (isA<processorPolyPatch>(pbMesh[p.patch(p.face())]))
361 td.switchProcessor =
true;
367 td.cloud().functions().postMove(p, cellI, dt, start, td.keepParticle);
370 return td.keepParticle;
374 template<
class ParcelType>
375 template<
class TrackData>
378 typename TrackData::cloudType::parcelType& p =
379 static_cast<typename TrackData::cloudType::parcelType&
>(*this);
381 td.cloud().functions().postFace(p, p.face(), td.keepParticle);
385 template<
class ParcelType>
390 template<
class ParcelType>
391 template<
class TrackData>
397 const scalar trackFraction,
401 typename TrackData::cloudType::parcelType& p =
402 static_cast<typename TrackData::cloudType::parcelType&
>(*this);
405 td.cloud().functions().postPatch
415 if (td.cloud().surfaceFilm().transferParcel(p, pp, td.keepParticle))
423 return td.cloud().patchInteraction().correct
435 template<
class ParcelType>
436 template<
class TrackData>
443 td.switchProcessor =
true;
447 template<
class ParcelType>
448 template<
class TrackData>
460 template<
class ParcelType>
461 template<
class TrackData>
468 td.keepParticle =
false;
472 template<
class ParcelType>
475 ParcelType::transformProperties(T);
481 template<
class ParcelType>
487 ParcelType::transformProperties(separation);
491 template<
class ParcelType>
void hitProcessorPatch(const processorPolyPatch &, TrackData &td)
Overridable function to handle the particle hitting a.
vector Uc_
Velocity [m/s].
void hitFace(int &td)
Overridable function to handle the particle hitting a face.
bool active_
Active flag - tracking inactive when active = false.
vector UTurb_
Turbulent velocity fluctuation [m/s].
vector U_
Velocity of Parcel [m/s].
dimensioned< scalar > mag(const dimensioned< Type > &)
virtual void transformProperties(const tensor &T)
Transform the physical properties of the particle.
This function object calculates the forces and moments by integrating the pressure and skin-friction ...
Helper class to supply results of integration.
intWM_LABEL_SIZE_t label
A label is an int32_t or int64_t as specified by the pre-processor macro WM_LABEL_SIZE.
scalar Sp() const
Return const access to the implicit coefficient [kg/s].
scalar dTarget_
Target diameter [m].
forces(const forces &)
Disallow default bitwise copy construct.
scalar rho_
Density [kg/m3].
A patch is a list of labels that address the faces in the global face list.
scalar tTurb_
Time spent in turbulent eddy [s].
tmp< GeometricField< Type, fvPatchField, volMesh > > Su(const GeometricField< Type, fvPatchField, volMesh > &su, const GeometricField< Type, fvPatchField, volMesh > &vf)
const vector & Su() const
Return const access to the explicit contribution [kg.m/s2].
Ostream & endl(Ostream &os)
Add newline and flush stream.
Neighbour processor patch.
#define WarningIn(functionName)
Report a warning using Foam::Warning.
void constrainDirection(const polyMesh &mesh, const Vector< label > &dirs, vector &d)
Set the constrained components of directions/velocity to zero.
dimensionSet transform(const dimensionSet &)
label typeId_
Parcel type id.
const polyBoundaryMesh & boundaryMesh() const
Return boundary mesh.
void calc(TrackData &td, const scalar dt, const label cellI)
Update parcel properties over the time interval.
Type average() const
Return const access to the average.
void setCellValues(TrackData &td, const scalar dt, const label cellI)
Set cell values.
Mesh consisting of general polyhedral cells.
Type value() const
Return const access to the value.
bool hitPatch(const polyPatch &p, TrackData &td, const label patchI, const scalar trackFraction, const tetIndices &tetIs)
Overridable function to handle the particle hitting a patch.
scalar nParticle_
Number of particles in Parcel.
void constrainToMeshCentre(const polyMesh &mesh, point &pt)
Set the constrained components of position to mesh centre.
bool move(TrackData &td, const scalar trackTime)
Move the parcel.
Kinematic parcel class with rotational motion (as spherical particles only) and one/two-way coupling ...
const vector calcVelocity(TrackData &td, const scalar dt, const label cellI, const scalar Re, const scalar mu, const scalar mass, const vector &Su, vector &dUTrans, scalar &Spu) const
Calculate new particle velocity.
void hitWallPatch(const wallPolyPatch &, TrackData &td, const tetIndices &)
Overridable function to handle the particle hitting a wallPatch.
KinematicParcel(const polyMesh &mesh, const vector &position, const label cellI, const label tetFaceI, const label tetPtI)
Construct from owner, position, and cloud owner.
void cellValueSourceCorrection(TrackData &td, const scalar dt, const label cellI)
Correct cell values using latest transfer information.
scalar rhoc_
Density [kg/m3].
dimensioned< Type > min(const dimensioned< Type > &, const dimensioned< Type > &)
virtual scalar wallImpactDistance(const vector &n) const
The nearest distance to a wall that the particle can be.
Storage and named access for the indices of a tet which is part of the decomposition of a cell...
scalar muc_
Viscosity [Pa.s].
Helper container for force Su and Sp terms.
scalarField Re(const UList< complex > &cf)