ENH: improvements in the surface sampling infrastructure

- improvement documentation for surface sampling.

- can now specify alternative sampling scheme for obtaining the
  face values instead of just using the "cell" value. For example,

      sampleScheme    cellPoint;

  This can be useful for cases when the surface is close to a boundary
  cell and there are large gradients in the sampled field.

- distanceSurface now handles non-closed surfaces more robustly.
  Unknown regions (not inside or outside) are marked internally and
  excluded from consideration. This allows use of 'signed' surfaces
  where not previously possible.
This commit is contained in:
Mark Olesen
2018-05-07 11:29:00 +02:00
parent 5268b5e61d
commit b0648f2ba0
94 changed files with 4029 additions and 2885 deletions

View File

@ -35,9 +35,7 @@ License
namespace Foam namespace Foam
{ {
defineTypeNameAndDebug(pointMesh, 0); defineTypeNameAndDebug(pointMesh, 0);
} }
// * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * // // * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * //
@ -88,18 +86,6 @@ Foam::pointMesh::pointMesh(const polyMesh& pMesh)
} }
// * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * //
Foam::pointMesh::~pointMesh()
{
if (debug)
{
Pout<< "~pointMesh::pointMesh()"
<< endl;
}
}
// * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * // // * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
bool Foam::pointMesh::movePoints() bool Foam::pointMesh::movePoints()
@ -121,8 +107,7 @@ void Foam::pointMesh::updateMesh(const mapPolyMesh& mpm)
if (debug) if (debug)
{ {
Pout<< "pointMesh::updateMesh(const mapPolyMesh&): " Pout<< "pointMesh::updateMesh(const mapPolyMesh&): "
<< "Updating for topology changes." << endl; << "Updating for topology changes." << nl << endl;
Pout<< endl;
} }
boundary_.updateMesh(); boundary_.updateMesh();

View File

@ -60,13 +60,13 @@ class pointMesh
// Private Member Functions // Private Member Functions
//- Map all fields //- Map all fields
void mapFields(const mapPolyMesh&); void mapFields(const mapPolyMesh& mpm);
//- Disallow default bitwise copy construct //- No copy construct
pointMesh(const pointMesh&); pointMesh(const pointMesh&) = delete;
//- Disallow default bitwise assignment //- No copy assignment
void operator=(const pointMesh&); void operator=(const pointMesh&) = delete;
public: public:
@ -86,7 +86,7 @@ public:
//- Destructor //- Destructor
~pointMesh(); ~pointMesh() = default;
// Member Functions // Member Functions
@ -122,13 +122,13 @@ public:
} }
// Mesh motion // Mesh motion
//- Move points //- Move points
bool movePoints(); bool movePoints();
//- Update the mesh corresponding to given map //- Update the mesh corresponding to given map
void updateMesh(const mapPolyMesh& mpm); void updateMesh(const mapPolyMesh& mpm);
// Member Operators // Member Operators

View File

@ -34,25 +34,19 @@ void Foam::plane::calcPntAndVec(const scalarList& C)
{ {
point_ = vector((-C[3]/C[0]), 0, 0); point_ = vector((-C[3]/C[0]), 0, 0);
} }
else if (mag(C[1]) > VSMALL)
{
point_ = vector(0, (-C[3]/C[1]), 0);
}
else if (mag(C[2]) > VSMALL)
{
point_ = vector(0, 0, (-C[3]/C[2]));
}
else else
{ {
if (mag(C[1]) > VSMALL) FatalErrorInFunction
{ << "At least one plane coefficient must have a value"
point_ = vector(0, (-C[3]/C[1]), 0); << abort(FatalError);
}
else
{
if (mag(C[2]) > VSMALL)
{
point_ = vector(0, 0, (-C[3]/C[2]));
}
else
{
FatalErrorInFunction
<< "At least one plane coefficient must have a value"
<< abort(FatalError);
}
}
} }
normal_ = vector(C[0], C[1], C[2]); normal_ = vector(C[0], C[1], C[2]);
@ -127,7 +121,7 @@ Foam::plane::plane(const vector& normalVector)
else else
{ {
FatalErrorInFunction FatalErrorInFunction
<< "plane normal has zero length. basePoint:" << point_ << "plane normal has zero length. base point:" << point_
<< abort(FatalError); << abort(FatalError);
} }
} }
@ -148,7 +142,7 @@ Foam::plane::plane
if (magSqrNormalVector < VSMALL) if (magSqrNormalVector < VSMALL)
{ {
FatalErrorInFunction FatalErrorInFunction
<< "plane normal has zero length. basePoint:" << point_ << "plane normal has zero length. base point:" << point_
<< abort(FatalError); << abort(FatalError);
} }
@ -247,7 +241,7 @@ Foam::plane::plane(Istream& is)
else else
{ {
FatalErrorInFunction FatalErrorInFunction
<< "plane normal has zero length. basePoint:" << point_ << "plane normal has zero length. base point:" << point_
<< abort(FatalError); << abort(FatalError);
} }
} }

View File

@ -28,6 +28,40 @@ Description
Geometric class that creates a 3D plane and can return the intersection Geometric class that creates a 3D plane and can return the intersection
point between a line and the plane. point between a line and the plane.
Construction from a dictionary is driven by the \c planeType
For \c planeType as \c pointAndNormal :
\verbatim
pointAndNormalDict
{
point <point>; // or basePoint
normal <vector>; // or normalVector
}
\endverbatim
For \c planeType as \c embeddedPoints :
\verbatim
embeddedPointsDict
{
point1 <point>;
point2 <point>;
point3 <point>;
}
\endverbatim
For \c planeType with \c planeEquation coefficients
\f$ ax + by + cz + d = 0 \f$ :
\verbatim
planeEquationDict
{
a <scalar>;
b <scalar>;
c <scalar>;
d <scalar>;
}
\endverbatim
SourceFiles SourceFiles
plane.C plane.C
@ -63,10 +97,11 @@ public:
//- Side of the plane //- Side of the plane
enum side enum side
{ {
NORMAL, NORMAL = 1, //!< The front (or normal) side of the plane
FLIP FLIP = -1 //!< The back (or flip) side of the plane
}; };
//- A direction and a reference point //- A direction and a reference point
class ray class ray
{ {
@ -126,10 +161,12 @@ public:
//- Construct null. Does not set normal and point. //- Construct null. Does not set normal and point.
plane(); plane();
//- Construct from normal vector through the origin //- Construct from normal vector through the origin.
// The vector is normalised to a unit vector on input.
explicit plane(const vector& normalVector); explicit plane(const vector& normalVector);
//- Construct from normal vector and point in plane //- Construct from normal vector and point in plane.
// By default, the vector is normalised to a unit vector on input.
explicit plane explicit plane
( (
const point& basePoint, const point& basePoint,
@ -150,7 +187,7 @@ public:
explicit plane(const scalarList& C); explicit plane(const scalarList& C);
//- Construct from dictionary //- Construct from dictionary
explicit plane(const dictionary& planeDict); explicit plane(const dictionary& dict);
//- Construct from Istream. Assumes the base + normal notation. //- Construct from Istream. Assumes the base + normal notation.
explicit plane(Istream& is); explicit plane(Istream& is);

View File

@ -45,7 +45,7 @@ Description
\endtable \endtable
The values are assigned according to the phase-fraction field: The values are assigned according to the phase-fraction field:
- 1: apply \$fp_{hyd}\$f - 1: apply \f$p_{hyd}\f$
- 0: apply a zero-gradient condition - 0: apply a zero-gradient condition
Usage Usage

View File

@ -42,7 +42,7 @@ namespace Foam
class fvMesh; class fvMesh;
/*---------------------------------------------------------------------------*\ /*---------------------------------------------------------------------------*\
Class interpolationCell Declaration Class interpolationCell Declaration
\*---------------------------------------------------------------------------*/ \*---------------------------------------------------------------------------*/
template<class Type> template<class Type>

View File

@ -64,20 +64,20 @@ class volPointInterpolation
scalarListList pointWeights_; scalarListList pointWeights_;
// Boundary handling // Boundary handling
//- Boundary addressing //- Boundary addressing
autoPtr<primitivePatch> boundaryPtr_; autoPtr<primitivePatch> boundaryPtr_;
//- Per boundary face whether is on non-coupled patch //- Per boundary face whether is on non-coupled patch
boolList boundaryIsPatchFace_; boolList boundaryIsPatchFace_;
//- Per mesh(!) point whether is on non-coupled patch (on any //- Per mesh(!) point whether is on non-coupled patch (on any
// processor) // processor)
boolList isPatchPoint_; boolList isPatchPoint_;
//- Per boundary point the weights per pointFaces. //- Per boundary point the weights per pointFaces.
scalarListList boundaryPointWeights_; scalarListList boundaryPointWeights_;
// Private Member Functions // Private Member Functions
@ -113,11 +113,11 @@ class volPointInterpolation
GeometricField<Type, pointPatchField, pointMesh>& GeometricField<Type, pointPatchField, pointMesh>&
) const; ) const;
//- Disallow default bitwise copy construct //- No copy construct
volPointInterpolation(const volPointInterpolation&); volPointInterpolation(const volPointInterpolation&) = delete;
//- Disallow default bitwise assignment //- No copy assignment
void operator=(const volPointInterpolation&); void operator=(const volPointInterpolation&) = delete;
public: public:
@ -138,19 +138,19 @@ public:
// Member functions // Member functions
// Edit // Edit
//- Update mesh topology using the morph engine //- Update mesh topology using the morph engine
void updateMesh(const mapPolyMesh&); void updateMesh(const mapPolyMesh&);
//- Correct weighting factors for moving mesh. //- Correct weighting factors for moving mesh.
bool movePoints(); bool movePoints();
// Interpolation functions // Interpolation Functions
//- Interpolate volField using inverse distance weighting //- Interpolate volField using inverse distance weighting
// returning pointField // \return pointField
template<class Type> template<class Type>
tmp<GeometricField<Type, pointPatchField, pointMesh>> interpolate tmp<GeometricField<Type, pointPatchField, pointMesh>> interpolate
( (
@ -158,7 +158,7 @@ public:
) const; ) const;
//- Interpolate tmp<volField> using inverse distance weighting //- Interpolate tmp<volField> using inverse distance weighting
// returning pointField // \return pointField
template<class Type> template<class Type>
tmp<GeometricField<Type, pointPatchField, pointMesh>> interpolate tmp<GeometricField<Type, pointPatchField, pointMesh>> interpolate
( (
@ -188,7 +188,7 @@ public:
) const; ) const;
//- Interpolate dimensionedField using inverse distance weighting //- Interpolate dimensionedField using inverse distance weighting
// returning pointField // \return pointField
template<class Type> template<class Type>
tmp<DimensionedField<Type, pointMesh>> interpolate tmp<DimensionedField<Type, pointMesh>> interpolate
( (
@ -204,82 +204,82 @@ public:
) const; ) const;
// Low level // Low level
//- Interpolate internal field from volField to pointField //- Interpolate internal field from volField to pointField
// using inverse distance weighting // using inverse distance weighting
template<class Type> template<class Type>
void interpolateInternalField void interpolateInternalField
( (
const GeometricField<Type, fvPatchField, volMesh>&, const GeometricField<Type, fvPatchField, volMesh>&,
GeometricField<Type, pointPatchField, pointMesh>& GeometricField<Type, pointPatchField, pointMesh>&
) const; ) const;
//- Interpolate boundary field without applying constraints/boundary //- Interpolate boundary field without applying constraints/boundary
// conditions // conditions
template<class Type> template<class Type>
void interpolateBoundaryField void interpolateBoundaryField
( (
const GeometricField<Type, fvPatchField, volMesh>& vf, const GeometricField<Type, fvPatchField, volMesh>& vf,
GeometricField<Type, pointPatchField, pointMesh>& pf GeometricField<Type, pointPatchField, pointMesh>& pf
) const; ) const;
//- Interpolate boundary with constraints/boundary conditions //- Interpolate boundary with constraints/boundary conditions
template<class Type> template<class Type>
void interpolateBoundaryField void interpolateBoundaryField
( (
const GeometricField<Type, fvPatchField, volMesh>& vf, const GeometricField<Type, fvPatchField, volMesh>& vf,
GeometricField<Type, pointPatchField, pointMesh>& pf, GeometricField<Type, pointPatchField, pointMesh>& pf,
const bool overrideFixedValue const bool overrideFixedValue
) const; ) const;
//- Interpolate from volField to pointField //- Interpolate from volField to pointField
// using inverse distance weighting // using inverse distance weighting
template<class Type> template<class Type>
void interpolate void interpolate
( (
const GeometricField<Type, fvPatchField, volMesh>&, const GeometricField<Type, fvPatchField, volMesh>&,
GeometricField<Type, pointPatchField, pointMesh>& GeometricField<Type, pointPatchField, pointMesh>&
) const; ) const;
//- Interpolate volField using inverse distance weighting //- Interpolate volField using inverse distance weighting
// returning pointField with name. Optionally caches // returning pointField with name. Optionally caches
template<class Type> template<class Type>
tmp<GeometricField<Type, pointPatchField, pointMesh>> interpolate tmp<GeometricField<Type, pointPatchField, pointMesh>> interpolate
( (
const GeometricField<Type, fvPatchField, volMesh>&, const GeometricField<Type, fvPatchField, volMesh>&,
const word& name, const word& name,
const bool cache const bool cache
) const; ) const;
//- Interpolate dimensioned internal field from cells to points //- Interpolate dimensioned internal field from cells to points
// using inverse distance weighting // using inverse distance weighting
template<class Type> template<class Type>
void interpolateDimensionedInternalField void interpolateDimensionedInternalField
( (
const DimensionedField<Type, volMesh>& vf, const DimensionedField<Type, volMesh>& vf,
DimensionedField<Type, pointMesh>& pf DimensionedField<Type, pointMesh>& pf
) const; ) const;
//- Interpolate dimensionedField using inverse distance weighting //- Interpolate dimensionedField using inverse distance weighting
// returning pointField with name. Optionally caches // returning pointField with name. Optionally caches
template<class Type> template<class Type>
tmp<DimensionedField<Type, pointMesh>> interpolate tmp<DimensionedField<Type, pointMesh>> interpolate
( (
const DimensionedField<Type, volMesh>&, const DimensionedField<Type, volMesh>&,
const word& name, const word& name,
const bool cache const bool cache
) const; ) const;
// Interpolation for displacement (applies 2D correction) // Interpolation for displacement (applies 2D correction)
//- Interpolate from volField to pointField //- Interpolate from volField to pointField
// using inverse distance weighting // using inverse distance weighting
void interpolateDisplacement void interpolateDisplacement
( (
const volVectorField&, const volVectorField&,
pointVectorField& pointVectorField&
) const; ) const;
}; };

View File

@ -3,7 +3,7 @@
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration | \\ / O peration |
\\ / A nd | Copyright (C) 2011-2017 OpenFOAM Foundation \\ / A nd | Copyright (C) 2011-2017 OpenFOAM Foundation
\\/ M anipulation | Copyright (C) 2015-2017 OpenCFD Ltd. \\/ M anipulation | Copyright (C) 2015-2018 OpenCFD Ltd.
------------------------------------------------------------------------------- -------------------------------------------------------------------------------
License License
This file is part of OpenFOAM. This file is part of OpenFOAM.
@ -29,6 +29,7 @@ License
#include "volFields.H" #include "volFields.H"
#include "sampledSurface.H" #include "sampledSurface.H"
#include "surfaceWriter.H" #include "surfaceWriter.H"
#include "interpolationCell.H"
#include "interpolationCellPoint.H" #include "interpolationCellPoint.H"
// * * * * * * * * * * * * Protected Member Functions * * * * * * * * * * * // // * * * * * * * * * * * * Protected Member Functions * * * * * * * * * * * //
@ -100,18 +101,15 @@ Foam::functionObjects::fieldValues::surfaceFieldValue::getFieldValues
// Average // Average
const faceList& faces = surfacePtr_().faces(); const faceList& faces = surfacePtr_().faces();
tmp<Field<Type>> tavg auto tavg = tmp<Field<Type>>::New(faces.size(), Zero);
( auto& avg = tavg.ref();
new Field<Type>(faces.size(), Zero)
);
Field<Type>& avg = tavg.ref();
forAll(faces, facei) forAll(faces, facei)
{ {
const face& f = faces[facei]; const face& f = faces[facei];
forAll(f, fp) for (const label labi : f)
{ {
avg[facei] += intFld[f[fp]]; avg[facei] += intFld[labi];
} }
avg[facei] /= f.size(); avg[facei] /= f.size();
} }
@ -120,7 +118,9 @@ Foam::functionObjects::fieldValues::surfaceFieldValue::getFieldValues
} }
else else
{ {
return surfacePtr_().sample(fld); const interpolationCell<Type> interp(fld);
return surfacePtr_().sample(interp);
} }
} }
else else

View File

@ -19,22 +19,24 @@ sampledSet/array/arraySet.C
sampledSet/shortestPath/shortestPathSet.C sampledSet/shortestPath/shortestPathSet.C
surface/cuttingPlane/cuttingPlane.C surface/cuttingPlane/cuttingPlane.C
surface/distanceSurface/distanceSurface.C
surface/isoSurface/isoSurface.C surface/isoSurface/isoSurface.C
surface/isoSurface/isoSurfaceCell.C surface/isoSurface/isoSurfaceCell.C
surface/thresholdCellFaces/thresholdCellFaces.C surface/thresholdCellFaces/thresholdCellFaces.C
surface/triSurfaceMesh/discreteSurface.C surface/triSurfaceMesh/discreteSurface.C
surfMeshSampler/surfMeshSampler/surfMeshSampler.C surfMeshSample/surfMeshSample/surfMeshSample.C
surfMeshSampler/surfMeshSamplers/surfMeshSamplers.C surfMeshSample/surfMeshSamplers/surfMeshSamplers.C
surfMeshSampler/plane/surfMeshPlaneSampler.C surfMeshSample/distanceSurface/surfMeshSampleDistanceSurface.C
surfMeshSampler/triSurfaceMesh/surfMeshDiscreteSampler.C surfMeshSample/plane/surfMeshSamplePlane.C
surfMeshSample/triSurfaceMesh/surfMeshSampleDiscrete.C
sampledSurface/sampledPatch/sampledPatch.C sampledSurface/sampledPatch/sampledPatch.C
sampledSurface/sampledPatchInternalField/sampledPatchInternalField.C sampledSurface/sampledPatchInternalField/sampledPatchInternalField.C
sampledSurface/sampledPlane/sampledPlane.C sampledSurface/sampledPlane/sampledPlane.C
sampledSurface/isoSurface/sampledIsoSurface.C sampledSurface/isoSurface/sampledIsoSurface.C
sampledSurface/isoSurface/sampledIsoSurfaceCell.C sampledSurface/isoSurface/sampledIsoSurfaceCell.C
sampledSurface/distanceSurface/distanceSurface.C sampledSurface/distanceSurface/sampledDistanceSurface.C
sampledSurface/sampledCuttingPlane/sampledCuttingPlane.C sampledSurface/sampledCuttingPlane/sampledCuttingPlane.C
sampledSurface/sampledSurface/sampledSurface.C sampledSurface/sampledSurface/sampledSurface.C
sampledSurface/sampledSurfaces/sampledSurfaces.C sampledSurface/sampledSurfaces/sampledSurfaces.C

View File

@ -214,8 +214,7 @@ Foam::label Foam::probes::prepare()
{ {
probeDir = mesh_.time().path()/probeSubDir; probeDir = mesh_.time().path()/probeSubDir;
} }
// Remove ".." probeDir.clean(); // Remove unneeded ".."
probeDir.clean();
// ignore known fields, close streams for fields that no longer exist // ignore known fields, close streams for fields that no longer exist
forAllIter(HashPtrTable<OFstream>, probeFilePtrs_, iter) forAllIter(HashPtrTable<OFstream>, probeFilePtrs_, iter)

View File

@ -109,8 +109,7 @@ Foam::sampledSets::sampledSets
{ {
outputPath_ = outputPath_/mesh_.name(); outputPath_ = outputPath_/mesh_.name();
} }
// Remove ".." outputPath_.clean(); // Remove unneeded ".."
outputPath_.clean();
read(dict); read(dict);
} }
@ -145,8 +144,7 @@ Foam::sampledSets::sampledSets
{ {
outputPath_ = outputPath_/mesh_.name(); outputPath_ = outputPath_/mesh_.name();
} }
// Remove ".." outputPath_.clean(); // Remove unneeded ".."
outputPath_.clean();
read(dict); read(dict);
} }

View File

@ -0,0 +1,211 @@
/*---------------------------------------------------------------------------*\
========= |
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration |
\\ / A nd | Copyright (C) 2018 OpenCFD Ltd.
\\/ M anipulation |
-------------------------------------------------------------------------------
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 <http://www.gnu.org/licenses/>.
\*---------------------------------------------------------------------------*/
#include "sampledDistanceSurface.H"
#include "dictionary.H"
#include "volFields.H"
#include "volPointInterpolation.H"
#include "addToRunTimeSelectionTable.H"
#include "fvMesh.H"
#include "volumeType.H"
// * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * //
namespace Foam
{
defineTypeNameAndDebug(sampledDistanceSurface, 0);
addNamedToRunTimeSelectionTable
(
sampledSurface,
sampledDistanceSurface,
word,
distanceSurface
);
}
// * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * //
Foam::sampledDistanceSurface::sampledDistanceSurface
(
const word& name,
const polyMesh& mesh,
const dictionary& dict
)
:
sampledSurface(name, mesh, dict),
distanceSurface(name, mesh, dict),
average_(dict.lookupOrDefault("average", false)),
needsUpdate_(true)
{}
// * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
bool Foam::sampledDistanceSurface::needsUpdate() const
{
return needsUpdate_;
}
bool Foam::sampledDistanceSurface::expire()
{
if (debug)
{
Pout<< "sampledDistanceSurface::expire :"
<< " needsUpdate:" << needsUpdate_ << endl;
}
// Clear derived data
clearGeom();
// already marked as expired
if (needsUpdate_)
{
return false;
}
needsUpdate_ = true;
return true;
}
bool Foam::sampledDistanceSurface::update()
{
if (debug)
{
Pout<< "sampledDistanceSurface::update :"
<< " needsUpdate:" << needsUpdate_ << endl;
}
if (!needsUpdate_)
{
return false;
}
distanceSurface::createGeometry();
needsUpdate_ = false;
return true;
}
Foam::tmp<Foam::scalarField> Foam::sampledDistanceSurface::sample
(
const interpolation<scalar>& sampler
) const
{
return sampleOnFaces(sampler);
}
Foam::tmp<Foam::vectorField> Foam::sampledDistanceSurface::sample
(
const interpolation<vector>& sampler
) const
{
return sampleOnFaces(sampler);
}
Foam::tmp<Foam::sphericalTensorField> Foam::sampledDistanceSurface::sample
(
const interpolation<sphericalTensor>& sampler
) const
{
return sampleOnFaces(sampler);
}
Foam::tmp<Foam::symmTensorField> Foam::sampledDistanceSurface::sample
(
const interpolation<symmTensor>& sampler
) const
{
return sampleOnFaces(sampler);
}
Foam::tmp<Foam::tensorField> Foam::sampledDistanceSurface::sample
(
const interpolation<tensor>& sampler
) const
{
return sampleOnFaces(sampler);
}
Foam::tmp<Foam::scalarField> Foam::sampledDistanceSurface::interpolate
(
const interpolation<scalar>& interpolator
) const
{
return sampleOnPoints(interpolator);
}
Foam::tmp<Foam::vectorField> Foam::sampledDistanceSurface::interpolate
(
const interpolation<vector>& interpolator
) const
{
return sampleOnPoints(interpolator);
}
Foam::tmp<Foam::sphericalTensorField> Foam::sampledDistanceSurface::interpolate
(
const interpolation<sphericalTensor>& interpolator
) const
{
return sampleOnPoints(interpolator);
}
Foam::tmp<Foam::symmTensorField> Foam::sampledDistanceSurface::interpolate
(
const interpolation<symmTensor>& interpolator
) const
{
return sampleOnPoints(interpolator);
}
Foam::tmp<Foam::tensorField> Foam::sampledDistanceSurface::interpolate
(
const interpolation<tensor>& interpolator
) const
{
return sampleOnPoints(interpolator);
}
void Foam::sampledDistanceSurface::print(Ostream& os) const
{
os << "distanceSurface: " << name() << " :";
distanceSurface::print(os);
}
// ************************************************************************* //

View File

@ -2,8 +2,8 @@
========= | ========= |
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration | \\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation \\ / A nd | Copyright (C) 2018 OpenCFD Ltd.
\\/ M anipulation | Copyright (C) 2016-2017 OpenCFD Ltd. \\/ M anipulation |
------------------------------------------------------------------------------- -------------------------------------------------------------------------------
License License
This file is part of OpenFOAM. This file is part of OpenFOAM.
@ -22,25 +22,51 @@ License
along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>. along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>.
Class Class
Foam::distanceSurface Foam::sampledDistanceSurface
Description Description
A sampledSurface defined by a distance to a surface. A sampledSurface defined by a distance to a surface - using either
an isoSurfaceCell or an isoSurface.
This is often embedded as part of a sampled surfaces function object.
Usage
Example of function object partial specification:
\verbatim
surfaces
(
surface1
{
type dDistanceSurface;
}
);
\endverbatim
Where the sub-entries comprise:
\table
Property | Description | Required | Default
type | distanceSurface | yes |
distance | distance from surface | yes |
signed | apply sign for +ve/-ve distance | yes |
cell | use isoSurfaceCell algorithm | no | true
regularise | point snapping | yes |
average | cell values from averaged point values | no | false
bounds | limit with bounding box | no |
surfaceType | type of surface | yes |
surfaceName | name of surface in triSurface/ | no | dict name
\endtable
Uses either isoSurfaceCell or isoSurface.
SourceFiles SourceFiles
distanceSurface.C sampledDistanceSurface.C
\*---------------------------------------------------------------------------*/ \*---------------------------------------------------------------------------*/
#ifndef distanceSurface_H #ifndef sampledDistanceSurface_H
#define distanceSurface_H #define sampledDistanceSurface_H
#include "sampledSurface.H" #include "sampledSurface.H"
#include "searchableSurface.H" #include "distanceSurface.H"
#include "isoSurfaceCell.H"
#include "isoSurface.H"
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
@ -48,109 +74,59 @@ namespace Foam
{ {
/*---------------------------------------------------------------------------*\ /*---------------------------------------------------------------------------*\
Class distanceSurface Declaration Class sampledDistanceSurface Declaration
\*---------------------------------------------------------------------------*/ \*---------------------------------------------------------------------------*/
class distanceSurface class sampledDistanceSurface
: :
public sampledSurface public sampledSurface,
public distanceSurface
{ {
// Private data // Private data
//- Surface
const autoPtr<searchableSurface> surfPtr_;
//- Distance value
const scalar distance_;
//- Signed distance
const bool signed_;
//- Whether to use isoSurfaceCell or isoSurface
const bool cell_;
//- Whether to coarsen
const Switch regularise_;
//- Whether to recalculate cell values as average of point values //- Whether to recalculate cell values as average of point values
const Switch average_; const Switch average_;
//- Optional bounding box to trim triangles against
const boundBox bounds_;
//- If restricted to zones, name of this zone or a regular expression
keyType zoneKey_;
//- Track if the surface needs an update //- Track if the surface needs an update
mutable bool needsUpdate_; mutable bool needsUpdate_;
//- Distance to cell centres
autoPtr<volScalarField> cellDistancePtr_;
//- Distance to points
scalarField pointDistance_;
//- Constructed iso surface
autoPtr<isoSurfaceCell> isoSurfCellPtr_;
//- Constructed iso surface
autoPtr<isoSurface> isoSurfPtr_;
// Private Member Functions // Private Member Functions
//- Create iso surface //- Sample volume field onto surface faces
void createGeometry();
//- Sample field on faces
template<class Type> template<class Type>
tmp<Field<Type>> sampleField tmp<Field<Type>> sampleOnFaces
( (
const GeometricField<Type, fvPatchField, volMesh>& vField const interpolation<Type>& sampler
) const; ) const;
//- Interpolate volume field onto surface points
template<class Type> template<class Type>
tmp<Field<Type>> tmp<Field<Type>> sampleOnPoints
interpolateField(const interpolation<Type>&) const; (
const interpolation<Type>& interpolation
) const;
public: public:
//- Runtime type information //- Runtime type information
TypeName("distanceSurface"); TypeName("sampledDistanceSurface");
// Constructors // Constructors
//- Construct from dictionary //- Construct from dictionary
distanceSurface sampledDistanceSurface
( (
const word& name, const word& name,
const polyMesh& mesh, const polyMesh& mesh,
const dictionary& dict const dictionary& dict
); );
//- Construct from components
distanceSurface
(
const word& name,
const polyMesh& mesh,
const bool interpolate,
const word& surfaceType,
const word& surfaceName,
const scalar distance,
const bool signedDistance,
const bool cell,
const Switch regularise,
const Switch average,
const boundBox& bounds = boundBox::invertedBox
);
//- Destructor //- Destructor
virtual ~distanceSurface(); virtual ~sampledDistanceSurface() = default;
// Member Functions // Member Functions
@ -204,81 +180,76 @@ public:
} }
//- The underlying surface // Sample
const meshedSurface& surface() const
{
if (cell_)
{
return *isoSurfCellPtr_;
}
return *isoSurfPtr_; //- Sample volume field onto surface faces
}
//- Sample field on surface
virtual tmp<scalarField> sample virtual tmp<scalarField> sample
( (
const volScalarField& const interpolation<scalar>& sampler
) const; ) const;
//- Sample field on surface //- Sample volume field onto surface faces
virtual tmp<vectorField> sample virtual tmp<vectorField> sample
( (
const volVectorField& const interpolation<vector>& sampler
) const; ) const;
//- Sample field on surface //- Sample volume field onto surface faces
virtual tmp<sphericalTensorField> sample virtual tmp<sphericalTensorField> sample
( (
const volSphericalTensorField& const interpolation<sphericalTensor>& sampler
) const; ) const;
//- Sample field on surface //- Sample volume field onto surface faces
virtual tmp<symmTensorField> sample virtual tmp<symmTensorField> sample
( (
const volSymmTensorField& const interpolation<symmTensor>& sampler
) const; ) const;
//- Sample field on surface //- Sample volume field onto surface faces
virtual tmp<tensorField> sample virtual tmp<tensorField> sample
( (
const volTensorField& const interpolation<tensor>& sampler
) const; ) const;
//- Interpolate field on surface // Interpolate
//- Interpolate volume field onto surface points
virtual tmp<scalarField> interpolate virtual tmp<scalarField> interpolate
( (
const interpolation<scalar>& const interpolation<scalar>& interpolator
) const; ) const;
//- Interpolate field on surface //- Interpolate volume field onto surface points
virtual tmp<vectorField> interpolate virtual tmp<vectorField> interpolate
( (
const interpolation<vector>& const interpolation<vector>& interpolator
) const; ) const;
//- Interpolate field on surface //- Interpolate volume field onto surface points
virtual tmp<sphericalTensorField> interpolate virtual tmp<sphericalTensorField> interpolate
( (
const interpolation<sphericalTensor>& const interpolation<sphericalTensor>& interpolator
) const; ) const;
//- Interpolate field on surface //- Interpolate volume field onto surface points
virtual tmp<symmTensorField> interpolate virtual tmp<symmTensorField> interpolate
( (
const interpolation<symmTensor>& const interpolation<symmTensor>& interpolator
) const; ) const;
//- Interpolate field on surface //- Interpolate volume field onto surface points
virtual tmp<tensorField> interpolate virtual tmp<tensorField> interpolate
( (
const interpolation<tensor>& const interpolation<tensor>& interpolator
) const; ) const;
//- Write
virtual void print(Ostream&) const; // Output
//- Print information
virtual void print(Ostream& os) const;
}; };
@ -289,7 +260,7 @@ public:
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
#ifdef NoRepository #ifdef NoRepository
#include "distanceSurfaceTemplates.C" #include "sampledDistanceSurfaceTemplates.C"
#endif #endif
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //

View File

@ -3,7 +3,7 @@
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration | \\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation \\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\/ M anipulation | \\/ M anipulation | Copyright (C) 2018 OpenCFD Ltd.
------------------------------------------------------------------------------- -------------------------------------------------------------------------------
License License
This file is part of OpenFOAM. This file is part of OpenFOAM.
@ -23,7 +23,7 @@ License
\*---------------------------------------------------------------------------*/ \*---------------------------------------------------------------------------*/
#include "distanceSurface.H" #include "sampledDistanceSurface.H"
#include "volFieldsFwd.H" #include "volFieldsFwd.H"
#include "pointFields.H" #include "pointFields.H"
#include "volPointInterpolation.H" #include "volPointInterpolation.H"
@ -32,71 +32,39 @@ License
template<class Type> template<class Type>
Foam::tmp<Foam::Field<Type>> Foam::tmp<Foam::Field<Type>>
Foam::distanceSurface::sampleField Foam::sampledDistanceSurface::sampleOnFaces
( (
const GeometricField<Type, fvPatchField, volMesh>& vField const interpolation<Type>& sampler
) const ) const
{ {
if (cell_) return sampledSurface::sampleOnFaces
{ (
return tmp<Field<Type>> sampler,
( meshCells(),
new Field<Type>(vField, isoSurfCellPtr_().meshCells()) faces(),
); points()
} );
else
{
return tmp<Field<Type>>
(
new Field<Type>(vField, isoSurfPtr_().meshCells())
);
}
} }
template<class Type> template<class Type>
Foam::tmp<Foam::Field<Type>> Foam::tmp<Foam::Field<Type>>
Foam::distanceSurface::interpolateField Foam::sampledDistanceSurface::sampleOnPoints
( (
const interpolation<Type>& interpolator const interpolation<Type>& interpolator
) const ) const
{ {
const fvMesh& fvm = static_cast<const fvMesh&>(mesh()); // Assume volPointInterpolation for the point field!
const auto& volFld = interpolator.psi();
// Get fields to sample. Assume volPointInterpolation! auto tpointFld =
const GeometricField<Type, fvPatchField, volMesh>& volFld = volPointInterpolation::New(volFld.mesh()).interpolate(volFld);
interpolator.psi();
tmp<GeometricField<Type, pointPatchField, pointMesh>> pointFld return distanceSurface::interpolate
( (
volPointInterpolation::New(fvm).interpolate(volFld) (average_ ? pointAverage(tpointFld())() : volFld),
tpointFld()
); );
// Sample.
if (cell_)
{
return isoSurfCellPtr_().interpolate
(
(
average_
? pointAverage(pointFld())()
: volFld
),
pointFld()
);
}
else
{
return isoSurfPtr_().interpolate
(
(
average_
? pointAverage(pointFld())()
: volFld
),
pointFld()
);
}
} }

View File

@ -3,7 +3,7 @@
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration | \\ / O peration |
\\ / A nd | Copyright (C) 2011-2017 OpenFOAM Foundation \\ / A nd | Copyright (C) 2011-2017 OpenFOAM Foundation
\\/ M anipulation | Copyright (C) 2016-2017 OpenCFD Ltd. \\/ M anipulation | Copyright (C) 2016-2018 OpenCFD Ltd.
------------------------------------------------------------------------------- -------------------------------------------------------------------------------
License License
This file is part of OpenFOAM. This file is part of OpenFOAM.
@ -538,13 +538,13 @@ bool Foam::sampledIsoSurface::expire()
// Clear derived data // Clear derived data
clearGeom(); clearGeom();
// already marked as expired // Already marked as expired
if (prevTimeIndex_ == -1) if (prevTimeIndex_ == -1)
{ {
return false; return false;
} }
// force update // Force update
prevTimeIndex_ = -1; prevTimeIndex_ = -1;
return true; return true;
} }
@ -558,46 +558,46 @@ bool Foam::sampledIsoSurface::update()
Foam::tmp<Foam::scalarField> Foam::sampledIsoSurface::sample Foam::tmp<Foam::scalarField> Foam::sampledIsoSurface::sample
( (
const volScalarField& vField const interpolation<scalar>& sampler
) const ) const
{ {
return sampleField(vField); return sampleOnFaces(sampler);
} }
Foam::tmp<Foam::vectorField> Foam::sampledIsoSurface::sample Foam::tmp<Foam::vectorField> Foam::sampledIsoSurface::sample
( (
const volVectorField& vField const interpolation<vector>& sampler
) const ) const
{ {
return sampleField(vField); return sampleOnFaces(sampler);
} }
Foam::tmp<Foam::sphericalTensorField> Foam::sampledIsoSurface::sample Foam::tmp<Foam::sphericalTensorField> Foam::sampledIsoSurface::sample
( (
const volSphericalTensorField& vField const interpolation<sphericalTensor>& sampler
) const ) const
{ {
return sampleField(vField); return sampleOnFaces(sampler);
} }
Foam::tmp<Foam::symmTensorField> Foam::sampledIsoSurface::sample Foam::tmp<Foam::symmTensorField> Foam::sampledIsoSurface::sample
( (
const volSymmTensorField& vField const interpolation<symmTensor>& sampler
) const ) const
{ {
return sampleField(vField); return sampleOnFaces(sampler);
} }
Foam::tmp<Foam::tensorField> Foam::sampledIsoSurface::sample Foam::tmp<Foam::tensorField> Foam::sampledIsoSurface::sample
( (
const volTensorField& vField const interpolation<tensor>& sampler
) const ) const
{ {
return sampleField(vField); return sampleOnFaces(sampler);
} }
@ -606,7 +606,7 @@ Foam::tmp<Foam::scalarField> Foam::sampledIsoSurface::interpolate
const interpolation<scalar>& interpolator const interpolation<scalar>& interpolator
) const ) const
{ {
return interpolateField(interpolator); return sampleOnPoints(interpolator);
} }
@ -615,7 +615,7 @@ Foam::tmp<Foam::vectorField> Foam::sampledIsoSurface::interpolate
const interpolation<vector>& interpolator const interpolation<vector>& interpolator
) const ) const
{ {
return interpolateField(interpolator); return sampleOnPoints(interpolator);
} }
Foam::tmp<Foam::sphericalTensorField> Foam::sampledIsoSurface::interpolate Foam::tmp<Foam::sphericalTensorField> Foam::sampledIsoSurface::interpolate
@ -623,7 +623,7 @@ Foam::tmp<Foam::sphericalTensorField> Foam::sampledIsoSurface::interpolate
const interpolation<sphericalTensor>& interpolator const interpolation<sphericalTensor>& interpolator
) const ) const
{ {
return interpolateField(interpolator); return sampleOnPoints(interpolator);
} }
@ -632,7 +632,7 @@ Foam::tmp<Foam::symmTensorField> Foam::sampledIsoSurface::interpolate
const interpolation<symmTensor>& interpolator const interpolation<symmTensor>& interpolator
) const ) const
{ {
return interpolateField(interpolator); return sampleOnPoints(interpolator);
} }
@ -641,7 +641,7 @@ Foam::tmp<Foam::tensorField> Foam::sampledIsoSurface::interpolate
const interpolation<tensor>& interpolator const interpolation<tensor>& interpolator
) const ) const
{ {
return interpolateField(interpolator); return sampleOnPoints(interpolator);
} }

View File

@ -3,7 +3,7 @@
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration | \\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation \\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\/ M anipulation | Copyright (C) 2016 OpenCFD Ltd. \\/ M anipulation | Copyright (C) 2016-2018 OpenCFD Ltd.
------------------------------------------------------------------------------- -------------------------------------------------------------------------------
License License
This file is part of OpenFOAM. This file is part of OpenFOAM.
@ -29,6 +29,35 @@ Description
To be used in sampleSurfaces / functionObjects. Recalculates iso surface To be used in sampleSurfaces / functionObjects. Recalculates iso surface
only if time changes. only if time changes.
This is often embedded as part of a sampled surfaces function object.
Usage
Example of function object partial specification:
\verbatim
surfaces
(
surface1
{
type sampledIsoSurface;
cell false;
}
);
\endverbatim
Where the sub-entries comprise:
\table
Property | Description | Required | Default
type | sampledIsoSurface | yes |
isoField | field name for obtaining iso-surface | yes |
isoValue | value of iso-surface | yes |
mergeTol | tolerance for merging points | no | 1e-6
regularise | point snapping | yes |
average | cell values from averaged point values | no | false
bounds | limit with bounding box | no |
zone | limit to specified zone | no |
exposedPatchName | name for zone subset | partly |
\endtable
SourceFiles SourceFiles
sampledIsoSurface.C sampledIsoSurface.C
@ -84,30 +113,29 @@ class sampledIsoSurface
mutable autoPtr<isoSurface> surfPtr_; mutable autoPtr<isoSurface> surfPtr_;
// Recreated for every isoSurface // Recreated for every isoSurface
//- Time at last call, also track if surface needs an update //- Time at last call, also track if surface needs an update
mutable label prevTimeIndex_; mutable label prevTimeIndex_;
//- Cached volfield //- Cached volfield
mutable autoPtr<volScalarField> storedVolFieldPtr_; mutable autoPtr<volScalarField> storedVolFieldPtr_;
mutable const volScalarField* volFieldPtr_; mutable const volScalarField* volFieldPtr_;
//- Cached pointfield //- Cached pointfield
mutable const pointScalarField* pointFieldPtr_; mutable const pointScalarField* pointFieldPtr_;
// And on subsetted mesh // And on subsetted mesh
//- Cached submesh //- Cached submesh
mutable autoPtr<fvMeshSubset> subMeshPtr_; mutable autoPtr<fvMeshSubset> subMeshPtr_;
//- Cached volfield //- Cached volfield
mutable autoPtr<volScalarField> storedVolSubFieldPtr_; mutable autoPtr<volScalarField> storedVolSubFieldPtr_;
mutable const volScalarField* volSubFieldPtr_; mutable const volScalarField* volSubFieldPtr_;
//- Cached pointfield
mutable const pointScalarField* pointSubFieldPtr_;
//- Cached pointfield
mutable const pointScalarField* pointSubFieldPtr_;
// Private Member Functions // Private Member Functions
@ -119,17 +147,19 @@ class sampledIsoSurface
// Do nothing (and return false) if no update was needed // Do nothing (and return false) if no update was needed
bool updateGeometry() const; bool updateGeometry() const;
//- Sample field on faces //- Sample volume field onto surface faces
template<class Type> template<class Type>
tmp<Field<Type>> sampleField tmp<Field<Type>> sampleOnFaces
( (
const GeometricField<Type, fvPatchField, volMesh>& vField const interpolation<Type>& sampler
) const; ) const;
//- Interpolate volume field onto surface points
template<class Type> template<class Type>
tmp<Field<Type>> tmp<Field<Type>> sampleOnPoints
interpolateField(const interpolation<Type>&) const; (
const interpolation<Type>& interpolator
) const;
public: public:
@ -217,67 +247,67 @@ public:
// Sample // Sample
//- Sample field on surface //- Sample volume field onto surface faces
virtual tmp<scalarField> sample virtual tmp<scalarField> sample
( (
const volScalarField& const interpolation<scalar>& sampler
) const; ) const;
//- Sample field on surface //- Sample volume field onto surface faces
virtual tmp<vectorField> sample virtual tmp<vectorField> sample
( (
const volVectorField& const interpolation<vector>& sampler
) const; ) const;
//- Sample field on surface //- Sample volume field onto surface faces
virtual tmp<sphericalTensorField> sample virtual tmp<sphericalTensorField> sample
( (
const volSphericalTensorField& const interpolation<sphericalTensor>& sampler
) const; ) const;
//- Sample field on surface //- Sample volume field onto surface faces
virtual tmp<symmTensorField> sample virtual tmp<symmTensorField> sample
( (
const volSymmTensorField& const interpolation<symmTensor>& sampler
) const; ) const;
//- Sample field on surface //- Sample volume field onto surface faces
virtual tmp<tensorField> sample virtual tmp<tensorField> sample
( (
const volTensorField& const interpolation<tensor>& sampler
) const; ) const;
// Interpolate // Interpolate
//- Interpolate field on surface //- Interpolate volume field onto surface points
virtual tmp<scalarField> interpolate virtual tmp<scalarField> interpolate
( (
const interpolation<scalar>& const interpolation<scalar>& interpolator
) const; ) const;
//- Interpolate field on surface //- Interpolate volume field onto surface points
virtual tmp<vectorField> interpolate virtual tmp<vectorField> interpolate
( (
const interpolation<vector>& const interpolation<vector>& interpolator
) const; ) const;
//- Interpolate field on surface //- Interpolate volume field onto surface points
virtual tmp<sphericalTensorField> interpolate virtual tmp<sphericalTensorField> interpolate
( (
const interpolation<sphericalTensor>& const interpolation<sphericalTensor>& interpolator
) const; ) const;
//- Interpolate field on surface //- Interpolate volume field onto surface points
virtual tmp<symmTensorField> interpolate virtual tmp<symmTensorField> interpolate
( (
const interpolation<symmTensor>& const interpolation<symmTensor>& interpolator
) const; ) const;
//- Interpolate field on surface //- Interpolate volume field onto surface points
virtual tmp<tensorField> interpolate virtual tmp<tensorField> interpolate
( (
const interpolation<tensor>& const interpolation<tensor>& interpolator
) const; ) const;

View File

@ -3,7 +3,7 @@
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration | \\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation \\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\/ M anipulation | Copyright (C) 2016-2017 OpenCFD Ltd. \\/ M anipulation | Copyright (C) 2016-2018 OpenCFD Ltd.
------------------------------------------------------------------------------- -------------------------------------------------------------------------------
License License
This file is part of OpenFOAM. This file is part of OpenFOAM.
@ -51,7 +51,7 @@ bool Foam::sampledIsoSurfaceCell::updateGeometry() const
{ {
const fvMesh& fvm = static_cast<const fvMesh&>(mesh()); const fvMesh& fvm = static_cast<const fvMesh&>(mesh());
// no update needed // No update needed
if (fvm.time().timeIndex() == prevTimeIndex_) if (fvm.time().timeIndex() == prevTimeIndex_)
{ {
return false; return false;
@ -62,76 +62,67 @@ bool Foam::sampledIsoSurfaceCell::updateGeometry() const
// Clear derived data // Clear derived data
sampledSurface::clearGeom(); sampledSurface::clearGeom();
// Optionally read volScalarField // Use field from database, or try to read it in
autoPtr<volScalarField> readFieldPtr_;
// 1. see if field in database const auto* cellFldPtr = fvm.lookupObjectPtr<volScalarField>(isoField_);
// 2. see if field can be read
const volScalarField* cellFldPtr = nullptr; if (debug)
if (fvm.foundObject<volScalarField>(isoField_))
{ {
if (debug) if (cellFldPtr)
{ {
InfoInFunction << "Lookup " << isoField_ << endl; InfoInFunction << "Lookup " << isoField_ << endl;
} }
else
cellFldPtr = &fvm.lookupObject<volScalarField>(isoField_);
}
else
{
// Bit of a hack. Read field and store.
if (debug)
{ {
InfoInFunction InfoInFunction
<< "Reading " << isoField_ << "Reading " << isoField_
<< " from time " <<fvm.time().timeName() << " from time " << fvm.time().timeName()
<< endl; << endl;
} }
readFieldPtr_.reset
(
new volScalarField
(
IOobject
(
isoField_,
fvm.time().timeName(),
fvm,
IOobject::MUST_READ,
IOobject::NO_WRITE,
false
),
fvm
)
);
cellFldPtr = readFieldPtr_.operator->();
} }
const volScalarField& cellFld = *cellFldPtr;
tmp<pointScalarField> pointFld // For holding the volScalarField read in.
( autoPtr<volScalarField> fieldReadPtr;
volPointInterpolation::New(fvm).interpolate(cellFld)
); if (!cellFldPtr)
{
// Bit of a hack. Read field and store.
fieldReadPtr = autoPtr<volScalarField>::New
(
IOobject
(
isoField_,
fvm.time().timeName(),
fvm,
IOobject::MUST_READ,
IOobject::NO_WRITE,
false
),
fvm
);
}
const volScalarField& cellFld =
(fieldReadPtr.valid() ? *fieldReadPtr : *cellFldPtr);
auto tpointFld = volPointInterpolation::New(fvm).interpolate(cellFld);
if (average_) if (average_)
{ {
//- From point field and interpolated cell. //- From point field and interpolated cell.
scalarField cellAvg(fvm.nCells(), scalar(0.0)); scalarField cellAvg(fvm.nCells(), Zero);
labelField nPointCells(fvm.nCells(), 0); labelField nPointCells(fvm.nCells(), Zero);
for (label pointi = 0; pointi < fvm.nPoints(); ++pointi)
{ {
for (label pointi = 0; pointi < fvm.nPoints(); pointi++) const scalar& val = tpointFld().primitiveField()[pointi];
const labelList& pCells = fvm.pointCells(pointi);
for (const label celli : pCells)
{ {
const labelList& pCells = fvm.pointCells(pointi); cellAvg[celli] += val;
++nPointCells[celli];
forAll(pCells, i)
{
label celli = pCells[i];
cellAvg[celli] += pointFld().primitiveField()[pointi];
nPointCells[celli]++;
}
} }
} }
forAll(cellAvg, celli) forAll(cellAvg, celli)
@ -139,11 +130,11 @@ bool Foam::sampledIsoSurfaceCell::updateGeometry() const
cellAvg[celli] /= nPointCells[celli]; cellAvg[celli] /= nPointCells[celli];
} }
isoSurfaceCell iso isoSurfaceCell surf
( (
fvm, fvm,
cellAvg, cellAvg,
pointFld().primitiveField(), tpointFld().primitiveField(),
isoVal_, isoVal_,
regularise_, regularise_,
bounds_ bounds_
@ -152,17 +143,17 @@ bool Foam::sampledIsoSurfaceCell::updateGeometry() const
const_cast<sampledIsoSurfaceCell&> const_cast<sampledIsoSurfaceCell&>
( (
*this *this
).transfer(static_cast<meshedSurface&>(iso)); ).transfer(static_cast<meshedSurface&>(surf));
meshCells_ = iso.meshCells(); meshCells_.transfer(surf.meshCells());
} }
else else
{ {
//- Direct from cell field and point field. Gives bad continuity. //- Direct from cell field and point field. Gives bad continuity.
isoSurfaceCell iso isoSurfaceCell surf
( (
fvm, fvm,
cellFld.primitiveField(), cellFld.primitiveField(),
pointFld().primitiveField(), tpointFld().primitiveField(),
isoVal_, isoVal_,
regularise_, regularise_,
bounds_ bounds_
@ -171,8 +162,8 @@ bool Foam::sampledIsoSurfaceCell::updateGeometry() const
const_cast<sampledIsoSurfaceCell&> const_cast<sampledIsoSurfaceCell&>
( (
*this *this
).transfer(static_cast<meshedSurface&>(iso)); ).transfer(static_cast<meshedSurface&>(surf));
meshCells_ = iso.meshCells(); meshCells_.transfer(surf.meshCells());
} }
@ -212,7 +203,7 @@ Foam::sampledIsoSurfaceCell::sampledIsoSurfaceCell
average_(dict.lookupOrDefault("average", true)), average_(dict.lookupOrDefault("average", true)),
zoneKey_(keyType::null), zoneKey_(keyType::null),
prevTimeIndex_(-1), prevTimeIndex_(-1),
meshCells_(0) meshCells_()
{} {}
@ -237,13 +228,13 @@ bool Foam::sampledIsoSurfaceCell::expire()
// Clear derived data // Clear derived data
sampledSurface::clearGeom(); sampledSurface::clearGeom();
// already marked as expired // Already marked as expired
if (prevTimeIndex_ == -1) if (prevTimeIndex_ == -1)
{ {
return false; return false;
} }
// force update // Force update
prevTimeIndex_ = -1; prevTimeIndex_ = -1;
return true; return true;
} }
@ -258,50 +249,50 @@ bool Foam::sampledIsoSurfaceCell::update()
Foam::tmp<Foam::scalarField> Foam::tmp<Foam::scalarField>
Foam::sampledIsoSurfaceCell::sample Foam::sampledIsoSurfaceCell::sample
( (
const volScalarField& vField const interpolation<scalar>& sampler
) const ) const
{ {
return sampleField(vField); return sampleOnFaces(sampler);
} }
Foam::tmp<Foam::vectorField> Foam::tmp<Foam::vectorField>
Foam::sampledIsoSurfaceCell::sample Foam::sampledIsoSurfaceCell::sample
( (
const volVectorField& vField const interpolation<vector>& sampler
) const ) const
{ {
return sampleField(vField); return sampleOnFaces(sampler);
} }
Foam::tmp<Foam::sphericalTensorField> Foam::tmp<Foam::sphericalTensorField>
Foam::sampledIsoSurfaceCell::sample Foam::sampledIsoSurfaceCell::sample
( (
const volSphericalTensorField& vField const interpolation<sphericalTensor>& sampler
) const ) const
{ {
return sampleField(vField); return sampleOnFaces(sampler);
} }
Foam::tmp<Foam::symmTensorField> Foam::tmp<Foam::symmTensorField>
Foam::sampledIsoSurfaceCell::sample Foam::sampledIsoSurfaceCell::sample
( (
const volSymmTensorField& vField const interpolation<symmTensor>& sampler
) const ) const
{ {
return sampleField(vField); return sampleOnFaces(sampler);
} }
Foam::tmp<Foam::tensorField> Foam::tmp<Foam::tensorField>
Foam::sampledIsoSurfaceCell::sample Foam::sampledIsoSurfaceCell::sample
( (
const volTensorField& vField const interpolation<tensor>& sampler
) const ) const
{ {
return sampleField(vField); return sampleOnFaces(sampler);
} }
@ -311,7 +302,7 @@ Foam::sampledIsoSurfaceCell::interpolate
const interpolation<scalar>& interpolator const interpolation<scalar>& interpolator
) const ) const
{ {
return interpolateField(interpolator); return sampleOnPoints(interpolator);
} }
@ -321,7 +312,7 @@ Foam::sampledIsoSurfaceCell::interpolate
const interpolation<vector>& interpolator const interpolation<vector>& interpolator
) const ) const
{ {
return interpolateField(interpolator); return sampleOnPoints(interpolator);
} }
Foam::tmp<Foam::sphericalTensorField> Foam::tmp<Foam::sphericalTensorField>
@ -330,7 +321,7 @@ Foam::sampledIsoSurfaceCell::interpolate
const interpolation<sphericalTensor>& interpolator const interpolation<sphericalTensor>& interpolator
) const ) const
{ {
return interpolateField(interpolator); return sampleOnPoints(interpolator);
} }
@ -340,7 +331,7 @@ Foam::sampledIsoSurfaceCell::interpolate
const interpolation<symmTensor>& interpolator const interpolation<symmTensor>& interpolator
) const ) const
{ {
return interpolateField(interpolator); return sampleOnPoints(interpolator);
} }
@ -350,7 +341,7 @@ Foam::sampledIsoSurfaceCell::interpolate
const interpolation<tensor>& interpolator const interpolation<tensor>& interpolator
) const ) const
{ {
return interpolateField(interpolator); return sampleOnPoints(interpolator);
} }

View File

@ -29,6 +29,33 @@ Description
To be used in sampleSurfaces / functionObjects. Recalculates iso surface To be used in sampleSurfaces / functionObjects. Recalculates iso surface
only if time changes. only if time changes.
This is often embedded as part of a sampled surfaces function object.
Usage
Example of function object partial specification:
\verbatim
surfaces
(
surface1
{
type sampledIsoSurfaceCell;
cell true;
}
);
\endverbatim
Where the sub-entries comprise:
\table
Property | Description | Required | Default
type | sampledIsoSurfaceCell | yes |
isoField | field name for obtaining iso-surface | yes |
isoValue | value of iso-surface | yes |
mergeTol | tolerance for merging points | no | 1e-6
regularise | point snapping | yes |
average | cell values from averaged point values | no | false
bounds | limit with bounding box | no |
\endtable
SourceFiles SourceFiles
sampledIsoSurfaceCell.C sampledIsoSurfaceCell.C
@ -79,13 +106,13 @@ class sampledIsoSurfaceCell
keyType zoneKey_; keyType zoneKey_;
// Recreated for every isoSurface // Recreated for every isoSurface
//- Time at last call, also track it surface needs an update //- Time at last call, also track it surface needs an update
mutable label prevTimeIndex_; mutable label prevTimeIndex_;
//- For every triangle the original cell in mesh //- For every triangle the original cell in mesh
mutable labelList meshCells_; mutable labelList meshCells_;
// Private Member Functions // Private Member Functions
@ -94,17 +121,19 @@ class sampledIsoSurfaceCell
// Do nothing (and return false) if no update was needed // Do nothing (and return false) if no update was needed
bool updateGeometry() const; bool updateGeometry() const;
//- Sample field on faces //- Sample volume field onto surface faces
template<class Type> template<class Type>
tmp<Field<Type>> sampleField tmp<Field<Type>> sampleOnFaces
( (
const GeometricField<Type, fvPatchField, volMesh>& vField const interpolation<Type>& sampler
) const; ) const;
//- Interpolate volume field onto surface points
template<class Type> template<class Type>
tmp<Field<Type>> tmp<Field<Type>> sampleOnPoints
interpolateField(const interpolation<Type>&) const; (
const interpolation<Type>& interpolator
) const;
public: public:
@ -180,65 +209,69 @@ public:
} }
//- Sample field on surface // Sample
//- Sample volume field onto surface faces
virtual tmp<scalarField> sample virtual tmp<scalarField> sample
( (
const volScalarField& const interpolation<scalar>& sampler
) const; ) const;
//- Sample field on surface //- Sample volume field onto surface faces
virtual tmp<vectorField> sample virtual tmp<vectorField> sample
( (
const volVectorField& const interpolation<vector>& sampler
) const; ) const;
//- Sample field on surface //- Sample volume field onto surface faces
virtual tmp<sphericalTensorField> sample virtual tmp<sphericalTensorField> sample
( (
const volSphericalTensorField& const interpolation<sphericalTensor>& sampler
) const; ) const;
//- Sample field on surface //- Sample volume field onto surface faces
virtual tmp<symmTensorField> sample virtual tmp<symmTensorField> sample
( (
const volSymmTensorField& const interpolation<symmTensor>& sampler
) const; ) const;
//- Sample field on surface //- Sample volume field onto surface faces
virtual tmp<tensorField> sample virtual tmp<tensorField> sample
( (
const volTensorField& const interpolation<tensor>& sampler
) const; ) const;
//- Interpolate field on surface // Interpolate
//- Interpolate volume field onto surface points
virtual tmp<scalarField> interpolate virtual tmp<scalarField> interpolate
( (
const interpolation<scalar>& const interpolation<scalar>& interpolator
) const; ) const;
//- Interpolate field on surface //- Interpolate volume field onto surface points
virtual tmp<vectorField> interpolate virtual tmp<vectorField> interpolate
( (
const interpolation<vector>& const interpolation<vector>& interpolator
) const; ) const;
//- Interpolate field on surface //- Interpolate volume field onto surface points
virtual tmp<sphericalTensorField> interpolate virtual tmp<sphericalTensorField> interpolate
( (
const interpolation<sphericalTensor>& const interpolation<sphericalTensor>& interpolator
) const; ) const;
//- Interpolate field on surface //- Interpolate volume field onto surface points
virtual tmp<symmTensorField> interpolate virtual tmp<symmTensorField> interpolate
( (
const interpolation<symmTensor>& const interpolation<symmTensor>& interpolator
) const; ) const;
//- Interpolate field on surface //- Interpolate volume field onto surface points
virtual tmp<tensorField> interpolate virtual tmp<tensorField> interpolate
( (
const interpolation<tensor>& const interpolation<tensor>& interpolator
) const; ) const;
//- Write //- Write

View File

@ -3,7 +3,7 @@
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration | \\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation \\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\/ M anipulation | \\/ M anipulation | Copyright (C) 2018 OpenCFD Ltd.
------------------------------------------------------------------------------- -------------------------------------------------------------------------------
License License
This file is part of OpenFOAM. This file is part of OpenFOAM.
@ -33,50 +33,57 @@ License
template<class Type> template<class Type>
Foam::tmp<Foam::Field<Type>> Foam::tmp<Foam::Field<Type>>
Foam::sampledIsoSurfaceCell::sampleField Foam::sampledIsoSurfaceCell::sampleOnFaces
( (
const GeometricField<Type, fvPatchField, volMesh>& vField const interpolation<Type>& sampler
) const ) const
{ {
// Recreate geometry if time has changed updateGeometry(); // Recreate geometry if time has changed
updateGeometry();
return tmp<Field<Type>>::New(vField, meshCells_); return sampledSurface::sampleOnFaces
(
sampler,
meshCells_,
faces(),
points()
);
} }
template<class Type> template<class Type>
Foam::tmp<Foam::Field<Type>> Foam::tmp<Foam::Field<Type>>
Foam::sampledIsoSurfaceCell::interpolateField Foam::sampledIsoSurfaceCell::sampleOnPoints
( (
const interpolation<Type>& interpolator const interpolation<Type>& interpolator
) const ) const
{ {
// Recreate geometry if time has changed updateGeometry(); // Recreate geometry if time has changed
updateGeometry();
const labelList& elements = meshCells_;
// One value per point // One value per point
tmp<Field<Type>> tvalues(new Field<Type>(points().size())); auto tvalues = tmp<Field<Type>>::New(points().size());
Field<Type>& values = tvalues.ref(); auto& values = tvalues.ref();
boolList pointDone(points().size(), false); const faceList& fcs = faces();
const pointField& pts = points();
bitSet pointDone(points().size());
forAll(faces(), cutFacei) forAll(faces(), cutFacei)
{ {
const face& f = faces()[cutFacei]; const face& f = fcs[cutFacei];
const label celli = elements[cutFacei];
forAll(f, faceVertI) for (const label pointi : f)
{ {
label pointi = f[faceVertI]; if (pointDone.set(pointi))
if (!pointDone[pointi])
{ {
values[pointi] = interpolator.interpolate values[pointi] = interpolator.interpolate
( (
points()[pointi], pts[pointi],
meshCells_[cutFacei] celli
); );
pointDone[pointi] = true;
} }
} }
} }

View File

@ -3,7 +3,7 @@
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration | \\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation \\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\/ M anipulation | \\/ M anipulation | Copyright (C) 2018 OpenCFD Ltd.
------------------------------------------------------------------------------- -------------------------------------------------------------------------------
License License
This file is part of OpenFOAM. This file is part of OpenFOAM.
@ -32,70 +32,59 @@ License
template<class Type> template<class Type>
Foam::tmp<Foam::Field<Type>> Foam::tmp<Foam::Field<Type>>
Foam::sampledIsoSurface::sampleField Foam::sampledIsoSurface::sampleOnFaces
( (
const GeometricField<Type, fvPatchField, volMesh>& vField const interpolation<Type>& sampler
) const ) const
{ {
// Recreate geometry if time has changed updateGeometry(); // Recreate geometry if time has changed
updateGeometry();
return tmp<Field<Type>>::New(vField, surface().meshCells()); return sampledSurface::sampleOnFaces
(
sampler,
surface().meshCells(),
surface(),
points()
);
} }
template<class Type> template<class Type>
Foam::tmp<Foam::Field<Type>> Foam::tmp<Foam::Field<Type>>
Foam::sampledIsoSurface::interpolateField Foam::sampledIsoSurface::sampleOnPoints
( (
const interpolation<Type>& interpolator const interpolation<Type>& interpolator
) const ) const
{ {
// Get fields to sample. Assume volPointInterpolation! updateGeometry(); // Recreate geometry if time has changed
const GeometricField<Type, fvPatchField, volMesh>& volFld =
interpolator.psi();
// Recreate geometry if time has changed // Assume volPointInterpolation for the point field!
updateGeometry(); const auto& volFld = interpolator.psi();
if (subMeshPtr_.valid()) if (subMeshPtr_.valid())
{ {
tmp<GeometricField<Type, fvPatchField, volMesh>> tvolSubFld = auto tvolSubFld = subMeshPtr_().interpolate(volFld);
subMeshPtr_().interpolate(volFld); const auto& volSubFld = tvolSubFld();
const GeometricField<Type, fvPatchField, volMesh>& volSubFld = auto tpointFld =
tvolSubFld();
tmp<GeometricField<Type, pointPatchField, pointMesh>> tpointSubFld =
volPointInterpolation::New(volSubFld.mesh()).interpolate(volSubFld); volPointInterpolation::New(volSubFld.mesh()).interpolate(volSubFld);
// Sample.
return surface().interpolate return surface().interpolate
( (
( (average_ ? pointAverage(tpointFld())() : volSubFld),
average_
? pointAverage(tpointSubFld())()
: volSubFld
),
tpointSubFld()
);
}
else
{
tmp<GeometricField<Type, pointPatchField, pointMesh>> tpointFld =
volPointInterpolation::New(volFld.mesh()).interpolate(volFld);
// Sample.
return surface().interpolate
(
(
average_
? pointAverage(tpointFld())()
: volFld
),
tpointFld() tpointFld()
); );
} }
auto tpointFld =
volPointInterpolation::New(volFld.mesh()).interpolate(volFld);
return surface().interpolate
(
(average_ ? pointAverage(tpointFld())() : volFld),
tpointFld()
);
} }

View File

@ -2,7 +2,7 @@
========= | ========= |
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration | \\ / O peration |
\\ / A nd | Copyright (C) 2015-2017 OpenCFD Ltd. \\ / A nd | Copyright (C) 2015-2018 OpenCFD Ltd.
\\/ M anipulation | \\/ M anipulation |
------------------------------------------------------------------------------- -------------------------------------------------------------------------------
License License
@ -164,21 +164,16 @@ Foam::tmp<Foam::Field<Type>> Foam::ensightSurfaceReader::readField
} }
} }
tmp<Field<Type>> tField(new Field<Type>(n, pTraits<Type>::zero)); auto tfield = tmp<Field<Type>>::New(n, Zero);
Field<Type>& field = tField.ref(); auto& field = tfield.ref();
for for (direction cmpti=0; cmpti < pTraits<Type>::nComponents; ++cmpti)
(
direction cmptI=0;
cmptI < pTraits<Type>::nComponents;
++cmptI
)
{ {
field.replace(cmptI, values[cmptI]); field.replace(cmpti, values[cmpti]);
values[cmptI].clear(); values[cmpti].clear();
} }
return tField; return tfield;
} }

View File

@ -3,7 +3,7 @@
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration | \\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation \\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\/ M anipulation | Copyright (C) 2016-2017 OpenCFD Ltd. \\/ M anipulation | Copyright (C) 2016-2018 OpenCFD Ltd.
------------------------------------------------------------------------------- -------------------------------------------------------------------------------
License License
This file is part of OpenFOAM. This file is part of OpenFOAM.
@ -386,50 +386,50 @@ bool Foam::sampledCuttingPlane::update()
Foam::tmp<Foam::scalarField> Foam::tmp<Foam::scalarField>
Foam::sampledCuttingPlane::sample Foam::sampledCuttingPlane::sample
( (
const volScalarField& vField const interpolation<scalar>& sampler
) const ) const
{ {
return sampleField(vField); return sampleOnFaces(sampler);
} }
Foam::tmp<Foam::vectorField> Foam::tmp<Foam::vectorField>
Foam::sampledCuttingPlane::sample Foam::sampledCuttingPlane::sample
( (
const volVectorField& vField const interpolation<vector>& sampler
) const ) const
{ {
return sampleField(vField); return sampleOnFaces(sampler);
} }
Foam::tmp<Foam::sphericalTensorField> Foam::tmp<Foam::sphericalTensorField>
Foam::sampledCuttingPlane::sample Foam::sampledCuttingPlane::sample
( (
const volSphericalTensorField& vField const interpolation<sphericalTensor>& sampler
) const ) const
{ {
return sampleField(vField); return sampleOnFaces(sampler);
} }
Foam::tmp<Foam::symmTensorField> Foam::tmp<Foam::symmTensorField>
Foam::sampledCuttingPlane::sample Foam::sampledCuttingPlane::sample
( (
const volSymmTensorField& vField const interpolation<symmTensor>& sampler
) const ) const
{ {
return sampleField(vField); return sampleOnFaces(sampler);
} }
Foam::tmp<Foam::tensorField> Foam::tmp<Foam::tensorField>
Foam::sampledCuttingPlane::sample Foam::sampledCuttingPlane::sample
( (
const volTensorField& vField const interpolation<tensor>& sampler
) const ) const
{ {
return sampleField(vField); return sampleOnFaces(sampler);
} }
@ -439,7 +439,7 @@ Foam::sampledCuttingPlane::interpolate
const interpolation<scalar>& interpolator const interpolation<scalar>& interpolator
) const ) const
{ {
return interpolateField(interpolator); return sampleOnPoints(interpolator);
} }
@ -449,16 +449,17 @@ Foam::sampledCuttingPlane::interpolate
const interpolation<vector>& interpolator const interpolation<vector>& interpolator
) const ) const
{ {
return interpolateField(interpolator); return sampleOnPoints(interpolator);
} }
Foam::tmp<Foam::sphericalTensorField> Foam::tmp<Foam::sphericalTensorField>
Foam::sampledCuttingPlane::interpolate Foam::sampledCuttingPlane::interpolate
( (
const interpolation<sphericalTensor>& interpolator const interpolation<sphericalTensor>& interpolator
) const ) const
{ {
return interpolateField(interpolator); return sampleOnPoints(interpolator);
} }
@ -468,7 +469,7 @@ Foam::sampledCuttingPlane::interpolate
const interpolation<symmTensor>& interpolator const interpolation<symmTensor>& interpolator
) const ) const
{ {
return interpolateField(interpolator); return sampleOnPoints(interpolator);
} }
@ -478,7 +479,7 @@ Foam::sampledCuttingPlane::interpolate
const interpolation<tensor>& interpolator const interpolation<tensor>& interpolator
) const ) const
{ {
return interpolateField(interpolator); return sampleOnPoints(interpolator);
} }

View File

@ -3,7 +3,7 @@
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration | \\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation \\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\/ M anipulation | Copyright (C) 2016 OpenCFD Ltd. \\/ M anipulation | Copyright (C) 2016-2018 OpenCFD Ltd.
------------------------------------------------------------------------------- -------------------------------------------------------------------------------
License License
This file is part of OpenFOAM. This file is part of OpenFOAM.
@ -26,7 +26,41 @@ Class
Description Description
A sampledSurface defined by a plane using the iso-surface algorithm A sampledSurface defined by a plane using the iso-surface algorithm
to 'cut' the mesh. to \a cut the mesh.
This is often embedded as part of a sampled surfaces function object.
Usage
Example of function object partial specification:
\verbatim
surfaces
(
surface1
{
type cuttingPlane;
planeType pointAndNormal;
pointAndNormalDict
{
...
}
}
);
\endverbatim
Where the sub-entries comprise:
\table
Property | Description | Required | Default
type | cuttingPlane | yes |
planeType | plane description (pointAndNormal etc) | yes |
mergeTol | tolerance for merging points | no | 1e-6
regularise | point snapping | no | true
bounds | limit with bounding box | no |
zone | limit to specified zone | no |
exposedPatchName | name for zone subset | partly |
\endtable
SeeAlso
Foam::plane
SourceFiles SourceFiles
sampledCuttingPlane.C sampledCuttingPlane.C
@ -49,7 +83,7 @@ namespace Foam
{ {
/*---------------------------------------------------------------------------*\ /*---------------------------------------------------------------------------*\
Class sampledCuttingPlane Declaration Class sampledCuttingPlane Declaration
\*---------------------------------------------------------------------------*/ \*---------------------------------------------------------------------------*/
class sampledCuttingPlane class sampledCuttingPlane
@ -93,7 +127,7 @@ class sampledCuttingPlane
scalarField pointDistance_; scalarField pointDistance_;
//- Constructed iso surface //- Constructed iso surface
//autoPtr<isoSurfaceCell> isoSurfPtr_; //autoPtr<isoSurfaceCell> isoSurfCellPtr_;
autoPtr<isoSurface> isoSurfPtr_; autoPtr<isoSurface> isoSurfPtr_;
@ -102,17 +136,19 @@ class sampledCuttingPlane
//- Create iso surface //- Create iso surface
void createGeometry(); void createGeometry();
//- Sample field on faces //- Sample volume field onto surface faces
template<class Type> template<class Type>
tmp<Field<Type>> sampleField tmp<Field<Type>> sampleOnFaces
( (
const GeometricField<Type, fvPatchField, volMesh>& vField const interpolation<Type>& sampler
) const; ) const;
//- Interpolate volume field onto surface points
template<class Type> template<class Type>
tmp<Field<Type>> tmp<Field<Type>> sampleOnPoints
interpolateField(const interpolation<Type>&) const; (
const interpolation<Type>& interpolator
) const;
public: public:
@ -193,76 +229,95 @@ public:
} }
//- The underlying surface
meshedSurface& surface()
{
return *isoSurfPtr_;
}
//- For each face, the original cell in mesh
const labelList& meshCells() const
{
return isoSurfPtr_->meshCells();
}
//- For each face, the original cell in mesh
labelList& meshCells()
{
return isoSurfPtr_->meshCells();
}
// Sample // Sample
//- Sample field on surface //- Sample volume field onto surface faces
virtual tmp<scalarField> sample virtual tmp<scalarField> sample
( (
const volScalarField& const interpolation<scalar>& sampler
) const; ) const;
//- Sample field on surface //- Sample volume field onto surface faces
virtual tmp<vectorField> sample virtual tmp<vectorField> sample
( (
const volVectorField& const interpolation<vector>& sampler
) const; ) const;
//- Sample field on surface //- Sample volume field onto surface faces
virtual tmp<sphericalTensorField> sample virtual tmp<sphericalTensorField> sample
( (
const volSphericalTensorField& const interpolation<sphericalTensor>& sampler
) const; ) const;
//- Sample field on surface //- Sample volume field onto surface faces
virtual tmp<symmTensorField> sample virtual tmp<symmTensorField> sample
( (
const volSymmTensorField& const interpolation<symmTensor>& sampler
) const; ) const;
//- Sample field on surface //- Sample volume field onto surface faces
virtual tmp<tensorField> sample virtual tmp<tensorField> sample
( (
const volTensorField& const interpolation<tensor>& sampler
) const; ) const;
// Interpolate // Interpolate
//- Interpolate field on surface //- Interpolate volume field onto surface points
virtual tmp<scalarField> interpolate virtual tmp<scalarField> interpolate
( (
const interpolation<scalar>& const interpolation<scalar>& interpolator
) const; ) const;
//- Interpolate field on surface //- Interpolate volume field onto surface points
virtual tmp<vectorField> interpolate virtual tmp<vectorField> interpolate
( (
const interpolation<vector>& const interpolation<vector>& interpolator
) const; ) const;
//- Interpolate field on surface //- Interpolate volume field onto surface points
virtual tmp<sphericalTensorField> interpolate virtual tmp<sphericalTensorField> interpolate
( (
const interpolation<sphericalTensor>& const interpolation<sphericalTensor>& interpolator
) const; ) const;
//- Interpolate field on surface //- Interpolate volume field onto surface points
virtual tmp<symmTensorField> interpolate virtual tmp<symmTensorField> interpolate
( (
const interpolation<symmTensor>& const interpolation<symmTensor>& interpolator
) const; ) const;
//- Interpolate field on surface //- Interpolate volume field onto surface points
virtual tmp<tensorField> interpolate virtual tmp<tensorField> interpolate
( (
const interpolation<tensor>& const interpolation<tensor>& interpolator
) const; ) const;
// Output // Output
//- Write //- Print information
virtual void print(Ostream&) const; virtual void print(Ostream& os) const;
}; };

View File

@ -3,7 +3,7 @@
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration | \\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation \\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\/ M anipulation | \\/ M anipulation | Copyright (C) 2018 OpenCFD Ltd.
------------------------------------------------------------------------------- -------------------------------------------------------------------------------
License License
This file is part of OpenFOAM. This file is part of OpenFOAM.
@ -32,66 +32,55 @@ License
template<class Type> template<class Type>
Foam::tmp<Foam::Field<Type>> Foam::tmp<Foam::Field<Type>>
Foam::sampledCuttingPlane::sampleField Foam::sampledCuttingPlane::sampleOnFaces
( (
const GeometricField<Type, fvPatchField, volMesh>& vField const interpolation<Type>& sampler
) const ) const
{ {
return tmp<Field<Type>>::New(vField, surface().meshCells()); return sampledSurface::sampleOnFaces
(
sampler,
meshCells(),
faces(),
points()
);
} }
template<class Type> template<class Type>
Foam::tmp<Foam::Field<Type>> Foam::tmp<Foam::Field<Type>>
Foam::sampledCuttingPlane::interpolateField Foam::sampledCuttingPlane::sampleOnPoints
( (
const interpolation<Type>& interpolator const interpolation<Type>& interpolator
) const ) const
{ {
// Get fields to sample. Assume volPointInterpolation! // Assume volPointInterpolation for the point field!
const GeometricField<Type, fvPatchField, volMesh>& volFld = const auto& volFld = interpolator.psi();
interpolator.psi();
if (subMeshPtr_.valid()) if (subMeshPtr_.valid())
{ {
tmp<GeometricField<Type, fvPatchField, volMesh>> tvolSubFld = auto tvolSubFld = subMeshPtr_().interpolate(volFld);
subMeshPtr_().interpolate(volFld); const auto& volSubFld = tvolSubFld();
const GeometricField<Type, fvPatchField, volMesh>& volSubFld = auto tpointFld =
tvolSubFld();
tmp<GeometricField<Type, pointPatchField, pointMesh>> tpointSubFld =
volPointInterpolation::New(volSubFld.mesh()).interpolate(volSubFld); volPointInterpolation::New(volSubFld.mesh()).interpolate(volSubFld);
// Sample.
return surface().interpolate return surface().interpolate
( (
( (average_ ? pointAverage(tpointFld())() : volSubFld),
average_
? pointAverage(tpointSubFld())()
: volSubFld
),
tpointSubFld()
);
}
else
{
tmp<GeometricField<Type, pointPatchField, pointMesh>> tpointFld
(
volPointInterpolation::New(volFld.mesh()).interpolate(volFld)
);
// Sample.
return surface().interpolate
(
(
average_
? pointAverage(tpointFld())()
: volFld
),
tpointFld() tpointFld()
); );
} }
auto tpointFld =
volPointInterpolation::New(volFld.mesh()).interpolate(volFld);
return surface().interpolate
(
(average_ ? pointAverage(tpointFld())() : volFld),
tpointFld()
);
} }

View File

@ -3,7 +3,7 @@
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration | \\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation \\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\/ M anipulation | \\/ M anipulation | Copyright (C) 2018 OpenCFD Ltd.
------------------------------------------------------------------------------- -------------------------------------------------------------------------------
License License
This file is part of OpenFOAM. This file is part of OpenFOAM.
@ -118,10 +118,8 @@ bool Foam::sampledPatch::update()
} }
label sz = 0; label sz = 0;
forAll(patchIDs(), i) for (const label patchi : patchIDs())
{ {
const label patchi = patchIDs()[i];
const polyPatch& pp = mesh().boundaryMesh()[patchi]; const polyPatch& pp = mesh().boundaryMesh()[patchi];
if (isA<emptyPolyPatch>(pp)) if (isA<emptyPolyPatch>(pp))
@ -156,7 +154,7 @@ bool Foam::sampledPatch::update()
patchIndex_[sz] = i; patchIndex_[sz] = i;
patchFaceLabels_[sz] = j; patchFaceLabels_[sz] = j;
meshFaceLabels[sz] = pp.start()+j; meshFaceLabels[sz] = pp.start()+j;
sz++; ++sz;
} }
} }
@ -224,46 +222,46 @@ void Foam::sampledPatch::remapFaces(const labelUList& faceMap)
Foam::tmp<Foam::scalarField> Foam::sampledPatch::sample Foam::tmp<Foam::scalarField> Foam::sampledPatch::sample
( (
const volScalarField& vField const interpolation<scalar>& sampler
) const ) const
{ {
return sampleField(vField); return sampleOnFaces(sampler);
} }
Foam::tmp<Foam::vectorField> Foam::sampledPatch::sample Foam::tmp<Foam::vectorField> Foam::sampledPatch::sample
( (
const volVectorField& vField const interpolation<vector>& sampler
) const ) const
{ {
return sampleField(vField); return sampleOnFaces(sampler);
} }
Foam::tmp<Foam::sphericalTensorField> Foam::sampledPatch::sample Foam::tmp<Foam::sphericalTensorField> Foam::sampledPatch::sample
( (
const volSphericalTensorField& vField const interpolation<sphericalTensor>& sampler
) const ) const
{ {
return sampleField(vField); return sampleOnFaces(sampler);
} }
Foam::tmp<Foam::symmTensorField> Foam::sampledPatch::sample Foam::tmp<Foam::symmTensorField> Foam::sampledPatch::sample
( (
const volSymmTensorField& vField const interpolation<symmTensor>& sampler
) const ) const
{ {
return sampleField(vField); return sampleOnFaces(sampler);
} }
Foam::tmp<Foam::tensorField> Foam::sampledPatch::sample Foam::tmp<Foam::tensorField> Foam::sampledPatch::sample
( (
const volTensorField& vField const interpolation<tensor>& sampler
) const ) const
{ {
return sampleField(vField); return sampleOnFaces(sampler);
} }
@ -272,7 +270,7 @@ Foam::tmp<Foam::scalarField> Foam::sampledPatch::sample
const surfaceScalarField& sField const surfaceScalarField& sField
) const ) const
{ {
return sampleField(sField); return sampleOnFaces(sField);
} }
@ -281,7 +279,7 @@ Foam::tmp<Foam::vectorField> Foam::sampledPatch::sample
const surfaceVectorField& sField const surfaceVectorField& sField
) const ) const
{ {
return sampleField(sField); return sampleOnFaces(sField);
} }
@ -290,7 +288,7 @@ Foam::tmp<Foam::sphericalTensorField> Foam::sampledPatch::sample
const surfaceSphericalTensorField& sField const surfaceSphericalTensorField& sField
) const ) const
{ {
return sampleField(sField); return sampleOnFaces(sField);
} }
@ -299,7 +297,7 @@ Foam::tmp<Foam::symmTensorField> Foam::sampledPatch::sample
const surfaceSymmTensorField& sField const surfaceSymmTensorField& sField
) const ) const
{ {
return sampleField(sField); return sampleOnFaces(sField);
} }
@ -308,7 +306,7 @@ Foam::tmp<Foam::tensorField> Foam::sampledPatch::sample
const surfaceTensorField& sField const surfaceTensorField& sField
) const ) const
{ {
return sampleField(sField); return sampleOnFaces(sField);
} }
@ -317,7 +315,7 @@ Foam::tmp<Foam::scalarField> Foam::sampledPatch::interpolate
const interpolation<scalar>& interpolator const interpolation<scalar>& interpolator
) const ) const
{ {
return interpolateField(interpolator); return sampleOnPoints(interpolator);
} }
@ -326,7 +324,7 @@ Foam::tmp<Foam::vectorField> Foam::sampledPatch::interpolate
const interpolation<vector>& interpolator const interpolation<vector>& interpolator
) const ) const
{ {
return interpolateField(interpolator); return sampleOnPoints(interpolator);
} }
@ -335,7 +333,7 @@ Foam::tmp<Foam::sphericalTensorField> Foam::sampledPatch::interpolate
const interpolation<sphericalTensor>& interpolator const interpolation<sphericalTensor>& interpolator
) const ) const
{ {
return interpolateField(interpolator); return sampleOnPoints(interpolator);
} }
@ -344,7 +342,7 @@ Foam::tmp<Foam::symmTensorField> Foam::sampledPatch::interpolate
const interpolation<symmTensor>& interpolator const interpolation<symmTensor>& interpolator
) const ) const
{ {
return interpolateField(interpolator); return sampleOnPoints(interpolator);
} }
@ -353,7 +351,7 @@ Foam::tmp<Foam::tensorField> Foam::sampledPatch::interpolate
const interpolation<tensor>& interpolator const interpolation<tensor>& interpolator
) const ) const
{ {
return interpolateField(interpolator); return sampleOnPoints(interpolator);
} }

View File

@ -27,6 +27,29 @@ Class
Description Description
A sampledSurface on patches. Non-triangulated by default. A sampledSurface on patches. Non-triangulated by default.
This is often embedded as part of a sampled surfaces function object.
Usage
Example of function object partial specification:
\verbatim
surfaces
(
surface1
{
type patch;
patches (inlet "outlet.*");
}
);
\endverbatim
Where the sub-entries comprise:
\table
Property | Description | Required | Default
type | patch | yes |
patches | patch selection as word/regex list | yes |
triangulate | triangulate faces | no | false
\endtable
SourceFiles SourceFiles
sampledPatch.C sampledPatch.C
@ -83,22 +106,27 @@ class sampledPatch
// Private Member Functions // Private Member Functions
//- Sample field on faces //- Sample boundary field (from volume field) onto surface faces
template<class Type> template<class Type>
tmp<Field<Type>> sampleField tmp<Field<Type>> sampleOnFaces
( (
const GeometricField<Type, fvPatchField, volMesh>& vField const interpolation<Type>& sampler
) const; ) const;
//- Sample surface field on faces //- Sample boundary field (from surface field) onto surface faces
template<class Type> template<class Type>
tmp<Field<Type>> sampleField tmp<Field<Type>> sampleOnFaces
( (
const GeometricField<Type, fvsPatchField, surfaceMesh>& sField const GeometricField<Type, fvsPatchField, surfaceMesh>& sField
) const; ) const;
//- Interpolate boundary field (from volume field) onto surface points
template<class Type> template<class Type>
tmp<Field<Type>> interpolateField(const interpolation<Type>&) const; tmp<Field<Type>> sampleOnPoints
(
const interpolation<Type>& interpolator
) const;
//- Re-map action on triangulation or cleanup //- Re-map action on triangulation or cleanup
virtual void remapFaces(const labelUList& faceMap); virtual void remapFaces(const labelUList& faceMap);
@ -206,100 +234,104 @@ public:
} }
// Sample // Sample
//- Sample field on surface //- Sample boundary of volume field onto surface faces
virtual tmp<scalarField> sample virtual tmp<scalarField> sample
( (
const volScalarField& const interpolation<scalar>& sampler
) const; ) const;
//- Sample field on surface //- Sample boundary of volume field onto surface faces
virtual tmp<vectorField> sample virtual tmp<vectorField> sample
( (
const volVectorField& const interpolation<vector>& sampler
) const; ) const;
//- Sample field on surface //- Sample boundary of volume field onto surface faces
virtual tmp<sphericalTensorField> sample virtual tmp<sphericalTensorField> sample
( (
const volSphericalTensorField& const interpolation<sphericalTensor>& sampler
) const; ) const;
//- Sample field on surface //- Sample boundary of volume field onto surface faces
virtual tmp<symmTensorField> sample virtual tmp<symmTensorField> sample
( (
const volSymmTensorField& const interpolation<symmTensor>& sampler
) const; ) const;
//- Sample field on surface //- Sample boundary of volume field onto surface faces
virtual tmp<tensorField> sample virtual tmp<tensorField> sample
( (
const volTensorField& const interpolation<tensor>& sampler
) const; ) const;
//- Surface sample field on surface
virtual tmp<scalarField> sample
(
const surfaceScalarField&
) const;
//- Surface Sample field on surface
virtual tmp<vectorField> sample
(
const surfaceVectorField&
) const;
//- Surface sample field on surface
virtual tmp<sphericalTensorField> sample
(
const surfaceSphericalTensorField&
) const;
//- Surface sample field on surface
virtual tmp<symmTensorField> sample
(
const surfaceSymmTensorField&
) const;
//- Surface sample field on surface
virtual tmp<tensorField> sample
(
const surfaceTensorField&
) const;
// Interpolate //- Sample boundary of surface field on surface
virtual tmp<scalarField> sample
(
const surfaceScalarField&
) const;
//- Interpolate field on surface //- Sample boundary of surface field on surface
virtual tmp<scalarField> interpolate virtual tmp<vectorField> sample
( (
const interpolation<scalar>& const surfaceVectorField&
) const; ) const;
//- Interpolate field on surface //- Sample boundary of surface field on surface
virtual tmp<vectorField> interpolate virtual tmp<sphericalTensorField> sample
( (
const interpolation<vector>& const surfaceSphericalTensorField&
) const; ) const;
//- Interpolate field on surface //- Sample boundary of surface field on surface
virtual tmp<sphericalTensorField> interpolate virtual tmp<symmTensorField> sample
( (
const interpolation<sphericalTensor>& const surfaceSymmTensorField&
) const; ) const;
//- Interpolate field on surface //- Sample boundary of surface field on surface
virtual tmp<symmTensorField> interpolate virtual tmp<tensorField> sample
( (
const interpolation<symmTensor>& const surfaceTensorField&
) const; ) const;
//- Interpolate field on surface
virtual tmp<tensorField> interpolate // Interpolate
(
const interpolation<tensor>& //- Interpolate boundary of volume field onto surface points
) const; virtual tmp<scalarField> interpolate
(
const interpolation<scalar>& interpolator
) const;
//- Interpolate boundary of volume field onto surface points
virtual tmp<vectorField> interpolate
(
const interpolation<vector>& interpolator
) const;
//- Interpolate boundary of volume field onto surface points
virtual tmp<sphericalTensorField> interpolate
(
const interpolation<sphericalTensor>& interpolator
) const;
//- Interpolate boundary of volume field onto surface points
virtual tmp<symmTensorField> interpolate
(
const interpolation<symmTensor>& interpolator
) const;
//- Interpolate boundary of volume field onto surface points
virtual tmp<tensorField> interpolate
(
const interpolation<tensor>& interpolator
) const;
// Output
//- Write //- Write
virtual void print(Ostream&) const; virtual void print(Ostream&) const;

View File

@ -3,7 +3,7 @@
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration | \\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation \\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\/ M anipulation | \\/ M anipulation | Copyright (C) 2018 OpenCFD Ltd.
------------------------------------------------------------------------------- -------------------------------------------------------------------------------
License License
This file is part of OpenFOAM. This file is part of OpenFOAM.
@ -29,19 +29,23 @@ License
template<class Type> template<class Type>
Foam::tmp<Foam::Field<Type>> Foam::tmp<Foam::Field<Type>>
Foam::sampledPatch::sampleField Foam::sampledPatch::sampleOnFaces
( (
const GeometricField<Type, fvPatchField, volMesh>& vField const interpolation<Type>& sampler
) const ) const
{ {
const auto& vField = sampler.psi();
// One value per face // One value per face
tmp<Field<Type>> tvalues(new Field<Type>(patchFaceLabels_.size())); auto tvalues = tmp<Field<Type>>::New(patchFaceLabels_.size());
Field<Type>& values = tvalues.ref(); auto& values = tvalues.ref();
forAll(patchFaceLabels_, i) forAll(patchFaceLabels_, i)
{ {
label patchi = patchIDs_[patchIndex_[i]]; const label patchi = patchIDs_[patchIndex_[i]];
const Field<Type>& bField = vField.boundaryField()[patchi]; const label patchFacei = patchFaceLabels_[i];
values[i] = bField[patchFaceLabels_[i]];
values[i] = vField.boundaryField()[patchi][patchFacei];
} }
return tvalues; return tvalues;
@ -50,19 +54,21 @@ Foam::sampledPatch::sampleField
template<class Type> template<class Type>
Foam::tmp<Foam::Field<Type>> Foam::tmp<Foam::Field<Type>>
Foam::sampledPatch::sampleField Foam::sampledPatch::sampleOnFaces
( (
const GeometricField<Type, fvsPatchField, surfaceMesh>& sField const GeometricField<Type, fvsPatchField, surfaceMesh>& sField
) const ) const
{ {
// One value per face // One value per face
tmp<Field<Type>> tvalues(new Field<Type>(patchFaceLabels_.size())); auto tvalues = tmp<Field<Type>>::New(patchFaceLabels_.size());
Field<Type>& values = tvalues.ref(); auto& values = tvalues.ref();
forAll(patchFaceLabels_, i) forAll(patchFaceLabels_, i)
{ {
label patchi = patchIDs_[patchIndex_[i]]; const label patchi = patchIDs_[patchIndex_[i]];
values[i] = sField.boundaryField()[patchi][patchFaceLabels_[i]]; const label patchFacei = patchFaceLabels_[i];
values[i] = sField.boundaryField()[patchi][patchFacei];
} }
return tvalues; return tvalues;
@ -71,34 +77,32 @@ Foam::sampledPatch::sampleField
template<class Type> template<class Type>
Foam::tmp<Foam::Field<Type>> Foam::tmp<Foam::Field<Type>>
Foam::sampledPatch::interpolateField Foam::sampledPatch::sampleOnPoints
( (
const interpolation<Type>& interpolator const interpolation<Type>& interpolator
) const ) const
{ {
// One value per vertex // One value per vertex
tmp<Field<Type>> tvalues(new Field<Type>(points().size())); auto tvalues = tmp<Field<Type>>::New(points().size());
Field<Type>& values = tvalues.ref(); auto& values = tvalues.ref();
const labelList& own = mesh().faceOwner(); const labelList& own = mesh().faceOwner();
boolList pointDone(points().size(), false); bitSet pointDone(points().size());
forAll(faces(), cutFacei) forAll(faces(), cutFacei)
{ {
label patchi = patchIDs_[patchIndex_[cutFacei]]; const label patchi = patchIDs_[patchIndex_[cutFacei]];
const polyPatch& pp = mesh().boundaryMesh()[patchi]; const polyPatch& pp = mesh().boundaryMesh()[patchi];
label patchFacei = patchFaceLabels()[cutFacei]; const label patchFacei = patchFaceLabels()[cutFacei];
const face& f = faces()[cutFacei]; const face& f = faces()[cutFacei];
forAll(f, faceVertI) for (const label pointi : f)
{ {
label pointi = f[faceVertI]; if (pointDone.set(pointi))
if (!pointDone[pointi])
{ {
label facei = patchFacei + pp.start(); const label facei = patchFacei + pp.start();
label celli = own[facei]; const label celli = own[facei];
values[pointi] = interpolator.interpolate values[pointi] = interpolator.interpolate
( (
@ -106,7 +110,6 @@ Foam::sampledPatch::interpolateField
celli, celli,
facei facei
); );
pointDone[pointi] = true;
} }
} }
} }

View File

@ -3,7 +3,7 @@
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration | \\ / O peration |
\\ / A nd | Copyright (C) 2011-2013 OpenFOAM Foundation \\ / A nd | Copyright (C) 2011-2013 OpenFOAM Foundation
\\/ M anipulation | \\/ M anipulation | Copyright (C) 2018 OpenCFD Ltd.
------------------------------------------------------------------------------- -------------------------------------------------------------------------------
License License
This file is part of OpenFOAM. This file is part of OpenFOAM.
@ -135,55 +135,50 @@ Foam::sampledPatchInternalField::sampledPatchInternalField
} }
// * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * //
Foam::sampledPatchInternalField::~sampledPatchInternalField()
{}
// * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * // // * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
Foam::tmp<Foam::scalarField> Foam::sampledPatchInternalField::sample Foam::tmp<Foam::scalarField> Foam::sampledPatchInternalField::sample
( (
const volScalarField& vField const interpolation<scalar>& sampler
) const ) const
{ {
return sampleField(vField); return sampleOnFaces(sampler);
} }
Foam::tmp<Foam::vectorField> Foam::sampledPatchInternalField::sample Foam::tmp<Foam::vectorField> Foam::sampledPatchInternalField::sample
( (
const volVectorField& vField const interpolation<vector>& sampler
) const ) const
{ {
return sampleField(vField); return sampleOnFaces(sampler);
} }
Foam::tmp<Foam::sphericalTensorField> Foam::sampledPatchInternalField::sample Foam::tmp<Foam::sphericalTensorField> Foam::sampledPatchInternalField::sample
( (
const volSphericalTensorField& vField const interpolation<sphericalTensor>& sampler
) const ) const
{ {
return sampleField(vField); return sampleOnFaces(sampler);
} }
Foam::tmp<Foam::symmTensorField> Foam::sampledPatchInternalField::sample Foam::tmp<Foam::symmTensorField> Foam::sampledPatchInternalField::sample
( (
const volSymmTensorField& vField const interpolation<symmTensor>& sampler
) const ) const
{ {
return sampleField(vField); return sampleOnFaces(sampler);
} }
Foam::tmp<Foam::tensorField> Foam::sampledPatchInternalField::sample Foam::tmp<Foam::tensorField> Foam::sampledPatchInternalField::sample
( (
const volTensorField& vField const interpolation<tensor>& sampler
) const ) const
{ {
return sampleField(vField); return sampleOnFaces(sampler);
} }
@ -192,7 +187,7 @@ Foam::tmp<Foam::scalarField> Foam::sampledPatchInternalField::interpolate
const interpolation<scalar>& interpolator const interpolation<scalar>& interpolator
) const ) const
{ {
return interpolateField(interpolator); return sampleOnPoints(interpolator);
} }
@ -201,7 +196,7 @@ Foam::tmp<Foam::vectorField> Foam::sampledPatchInternalField::interpolate
const interpolation<vector>& interpolator const interpolation<vector>& interpolator
) const ) const
{ {
return interpolateField(interpolator); return sampleOnPoints(interpolator);
} }
@ -211,7 +206,7 @@ Foam::sampledPatchInternalField::interpolate
const interpolation<sphericalTensor>& interpolator const interpolation<sphericalTensor>& interpolator
) const ) const
{ {
return interpolateField(interpolator); return sampleOnPoints(interpolator);
} }
@ -220,7 +215,7 @@ Foam::tmp<Foam::symmTensorField> Foam::sampledPatchInternalField::interpolate
const interpolation<symmTensor>& interpolator const interpolation<symmTensor>& interpolator
) const ) const
{ {
return interpolateField(interpolator); return sampleOnPoints(interpolator);
} }
@ -229,7 +224,7 @@ Foam::tmp<Foam::tensorField> Foam::sampledPatchInternalField::interpolate
const interpolation<tensor>& interpolator const interpolation<tensor>& interpolator
) const ) const
{ {
return interpolateField(interpolator); return sampleOnPoints(interpolator);
} }

View File

@ -3,7 +3,7 @@
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration | \\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation \\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\/ M anipulation | \\/ M anipulation | Copyright (C) 2018 OpenCFD Ltd.
------------------------------------------------------------------------------- -------------------------------------------------------------------------------
License License
This file is part of OpenFOAM. This file is part of OpenFOAM.
@ -32,6 +32,34 @@ Description
- interpolate=true : interpolate inside cell and interpolate to points - interpolate=true : interpolate inside cell and interpolate to points
There is no option to get interpolated value inside the cell on the faces. There is no option to get interpolated value inside the cell on the faces.
This is often embedded as part of a sampled surfaces function object.
Usage
Example of function object partial specification:
\verbatim
surfaces
(
surface1
{
type patchInternalField;
patches (inlet "outlet.*");
offsetMode normal;
distance 0.05;
}
);
\endverbatim
Where the sub-entries comprise:
\table
Property | Description | Required | Default
type | patchInternalField | yes |
patches | patch selection as word/regex list | yes |
offsetMode | normal/uniform/nonuniform | no | normal
distance | distance for normal offset | partly |
offset | point offset for uniform offset | partly |
offsets | point offsets for nonuniform offset | partly |
\endtable
SourceFiles SourceFiles
sampledPatchInternalField.C sampledPatchInternalField.C
@ -64,15 +92,19 @@ class sampledPatchInternalField
// Private Member Functions // Private Member Functions
//- Sample field on faces //- Sample volume field onto surface faces
template<class Type> template<class Type>
tmp<Field<Type>> sampleField tmp<Field<Type>> sampleOnFaces
( (
const GeometricField<Type, fvPatchField, volMesh>& vField const interpolation<Type>& sampler
) const; ) const;
//- Interpolate volume field onto surface points
template<class Type> template<class Type>
tmp<Field<Type>> interpolateField(const interpolation<Type>&) const; tmp<Field<Type>> sampleOnPoints
(
const interpolation<Type>& interpolator
) const;
public: public:
@ -93,79 +125,81 @@ public:
//- Destructor //- Destructor
virtual ~sampledPatchInternalField(); virtual ~sampledPatchInternalField() = default;
// Member Functions // Member Functions
// Sample // Sample
//- Sample field on surface //- Sample boundary of volume field onto surface faces
virtual tmp<scalarField> sample virtual tmp<scalarField> sample
( (
const volScalarField& const interpolation<scalar>& sampler
) const; ) const;
//- Sample field on surface //- Sample boundary of volume field onto surface faces
virtual tmp<vectorField> sample virtual tmp<vectorField> sample
( (
const volVectorField& const interpolation<vector>& sampler
) const; ) const;
//- Sample field on surface //- Sample boundary of volume field onto surface faces
virtual tmp<sphericalTensorField> sample virtual tmp<sphericalTensorField> sample
( (
const volSphericalTensorField& const interpolation<sphericalTensor>& sampler
) const; ) const;
//- Sample field on surface //- Sample boundary of volume field onto surface faces
virtual tmp<symmTensorField> sample virtual tmp<symmTensorField> sample
( (
const volSymmTensorField& const interpolation<symmTensor>& sampler
) const; ) const;
//- Sample field on surface //- Sample boundary of volume field onto surface faces
virtual tmp<tensorField> sample virtual tmp<tensorField> sample
( (
const volTensorField& const interpolation<tensor>& sampler
) const; ) const;
// Interpolate // Interpolate
//- Interpolate field on surface //- Interpolate boundary of volume field onto surface points
virtual tmp<scalarField> interpolate virtual tmp<scalarField> interpolate
( (
const interpolation<scalar>& const interpolation<scalar>& interpolator
) const; ) const;
//- Interpolate field on surface //- Interpolate boundary of volume field onto surface points
virtual tmp<vectorField> interpolate virtual tmp<vectorField> interpolate
( (
const interpolation<vector>& const interpolation<vector>& interpolator
) const; ) const;
//- Interpolate field on surface //- Interpolate boundary of volume field onto surface points
virtual tmp<sphericalTensorField> interpolate virtual tmp<sphericalTensorField> interpolate
( (
const interpolation<sphericalTensor>& const interpolation<sphericalTensor>& interpolator
) const; ) const;
//- Interpolate field on surface //- Interpolate boundary of volume field onto surface points
virtual tmp<symmTensorField> interpolate virtual tmp<symmTensorField> interpolate
( (
const interpolation<symmTensor>& const interpolation<symmTensor>& interpolator
) const; ) const;
//- Interpolate field on surface //- Interpolate boundary of volume field onto surface points
virtual tmp<tensorField> interpolate virtual tmp<tensorField> interpolate
( (
const interpolation<tensor>& const interpolation<tensor>& interpolator
) const; ) const;
//- Write // Output
virtual void print(Ostream&) const;
//- Print information
virtual void print(Ostream& os) const;
}; };

View File

@ -3,7 +3,7 @@
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration | \\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation \\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\/ M anipulation | \\/ M anipulation | Copyright (C) 2018 OpenCFD Ltd.
------------------------------------------------------------------------------- -------------------------------------------------------------------------------
License License
This file is part of OpenFOAM. This file is part of OpenFOAM.
@ -31,14 +31,16 @@ License
template<class Type> template<class Type>
Foam::tmp<Foam::Field<Type>> Foam::tmp<Foam::Field<Type>>
Foam::sampledPatchInternalField::sampleField Foam::sampledPatchInternalField::sampleOnFaces
( (
const GeometricField<Type, fvPatchField, volMesh>& vField const interpolation<Type>& sampler
) const ) const
{ {
const auto& vField = sampler.psi();
// One value per face // One value per face
tmp<Field<Type>> tvalues(new Field<Type>(patchFaceLabels().size())); auto tvalues = tmp<Field<Type>>::New(patchFaceLabels().size());
Field<Type>& values = tvalues.ref(); auto& values = tvalues.ref();
forAll(patchStart(), i) forAll(patchStart(), i)
{ {
@ -66,7 +68,7 @@ Foam::sampledPatchInternalField::sampleField
template<class Type> template<class Type>
Foam::tmp<Foam::Field<Type>> Foam::tmp<Foam::Field<Type>>
Foam::sampledPatchInternalField::interpolateField Foam::sampledPatchInternalField::sampleOnPoints
( (
const interpolation<Type>& interpolator const interpolation<Type>& interpolator
) const ) const
@ -118,9 +120,9 @@ Foam::sampledPatchInternalField::interpolateField
labelList meshFaceLabels(allPatchVals.size()); labelList meshFaceLabels(allPatchVals.size());
sz = 0; sz = 0;
forAll(patchIDs(), i) for (const label patchId : patchIDs())
{ {
const polyPatch& pp = mesh().boundaryMesh()[patchIDs()[i]]; const polyPatch& pp = mesh().boundaryMesh()[patchId];
forAll(pp, i) forAll(pp, i)
{ {
meshFaceLabels[sz++] = pp.start()+i; meshFaceLabels[sz++] = pp.start()+i;

View File

@ -3,7 +3,7 @@
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration | \\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation \\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\/ M anipulation | Copyright (C) 2017 OpenCFD Ltd. \\/ M anipulation | Copyright (C) 2017-2018 OpenCFD Ltd.
------------------------------------------------------------------------------- -------------------------------------------------------------------------------
License License
This file is part of OpenFOAM. This file is part of OpenFOAM.
@ -35,7 +35,13 @@ License
namespace Foam namespace Foam
{ {
defineTypeNameAndDebug(sampledPlane, 0); defineTypeNameAndDebug(sampledPlane, 0);
addNamedToRunTimeSelectionTable(sampledSurface, sampledPlane, word, plane); addNamedToRunTimeSelectionTable
(
sampledSurface,
sampledPlane,
word,
plane
);
} }
// * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * // // * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * //
@ -170,6 +176,7 @@ bool Foam::sampledPlane::update()
<< nl << endl; << nl << endl;
} }
labelList selectedCells(mesh().cellZones().findMatching(zoneKey_).toc()); labelList selectedCells(mesh().cellZones().findMatching(zoneKey_).toc());
bool fullMesh = returnReduce(selectedCells.empty(), andOp<bool>()); bool fullMesh = returnReduce(selectedCells.empty(), andOp<bool>());
@ -234,46 +241,46 @@ bool Foam::sampledPlane::update()
Foam::tmp<Foam::scalarField> Foam::sampledPlane::sample Foam::tmp<Foam::scalarField> Foam::sampledPlane::sample
( (
const volScalarField& vField const interpolation<scalar>& sampler
) const ) const
{ {
return sampleField(vField); return sampleOnFaces(sampler);
} }
Foam::tmp<Foam::vectorField> Foam::sampledPlane::sample Foam::tmp<Foam::vectorField> Foam::sampledPlane::sample
( (
const volVectorField& vField const interpolation<vector>& sampler
) const ) const
{ {
return sampleField(vField); return sampleOnFaces(sampler);
} }
Foam::tmp<Foam::sphericalTensorField> Foam::sampledPlane::sample Foam::tmp<Foam::sphericalTensorField> Foam::sampledPlane::sample
( (
const volSphericalTensorField& vField const interpolation<sphericalTensor>& sampler
) const ) const
{ {
return sampleField(vField); return sampleOnFaces(sampler);
} }
Foam::tmp<Foam::symmTensorField> Foam::sampledPlane::sample Foam::tmp<Foam::symmTensorField> Foam::sampledPlane::sample
( (
const volSymmTensorField& vField const interpolation<symmTensor>& sampler
) const ) const
{ {
return sampleField(vField); return sampleOnFaces(sampler);
} }
Foam::tmp<Foam::tensorField> Foam::sampledPlane::sample Foam::tmp<Foam::tensorField> Foam::sampledPlane::sample
( (
const volTensorField& vField const interpolation<tensor>& sampler
) const ) const
{ {
return sampleField(vField); return sampleOnFaces(sampler);
} }
@ -282,7 +289,7 @@ Foam::tmp<Foam::scalarField> Foam::sampledPlane::interpolate
const interpolation<scalar>& interpolator const interpolation<scalar>& interpolator
) const ) const
{ {
return interpolateField(interpolator); return sampleOnPoints(interpolator);
} }
@ -291,7 +298,7 @@ Foam::tmp<Foam::vectorField> Foam::sampledPlane::interpolate
const interpolation<vector>& interpolator const interpolation<vector>& interpolator
) const ) const
{ {
return interpolateField(interpolator); return sampleOnPoints(interpolator);
} }
Foam::tmp<Foam::sphericalTensorField> Foam::sampledPlane::interpolate Foam::tmp<Foam::sphericalTensorField> Foam::sampledPlane::interpolate
@ -299,7 +306,7 @@ Foam::tmp<Foam::sphericalTensorField> Foam::sampledPlane::interpolate
const interpolation<sphericalTensor>& interpolator const interpolation<sphericalTensor>& interpolator
) const ) const
{ {
return interpolateField(interpolator); return sampleOnPoints(interpolator);
} }
@ -308,7 +315,7 @@ Foam::tmp<Foam::symmTensorField> Foam::sampledPlane::interpolate
const interpolation<symmTensor>& interpolator const interpolation<symmTensor>& interpolator
) const ) const
{ {
return interpolateField(interpolator); return sampleOnPoints(interpolator);
} }
@ -317,7 +324,7 @@ Foam::tmp<Foam::tensorField> Foam::sampledPlane::interpolate
const interpolation<tensor>& interpolator const interpolation<tensor>& interpolator
) const ) const
{ {
return interpolateField(interpolator); return sampleOnPoints(interpolator);
} }

View File

@ -3,7 +3,7 @@
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration | \\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation \\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\/ M anipulation | Copyright (C) 2016 OpenCFD Ltd. \\/ M anipulation | Copyright (C) 2016-2018 OpenCFD Ltd.
------------------------------------------------------------------------------- -------------------------------------------------------------------------------
License License
This file is part of OpenFOAM. This file is part of OpenFOAM.
@ -25,8 +25,43 @@ Class
Foam::sampledPlane Foam::sampledPlane
Description Description
A sampledSurface defined by a plane which 'cuts' the mesh using the A sampledSurface defined by a plane which \a cuts the mesh using the
cuttingPlane alorithm. The plane is triangulated by default. cuttingPlane alorithm. The surface is triangulated by default.
This is often embedded as part of a sampled surfaces function object.
Usage
Example of function object partial specification:
\verbatim
surfaces
(
surface1
{
type plane;
planeType pointAndNormal;
pointAndNormalDict
{
...
}
}
);
\endverbatim
Where the sub-entries comprise:
\table
Property | Description | Required | Default
type | plane | yes |
planeType | plane description (pointAndNormal etc) | yes |
triangulate | triangulate faces | no | true
bounds | limit with bounding box | no |
zone | limit to specified zone | no |
coordinateSystem | plane relative to given coordinate system | no |
\endtable
SeeAlso
Foam::coordinateSystem
Foam::cuttingPlane
Foam::plane
Note Note
Does not actually cut until update() called. Does not actually cut until update() called.
@ -70,19 +105,22 @@ class sampledPlane
//- Track if the surface needs an update //- Track if the surface needs an update
mutable bool needsUpdate_; mutable bool needsUpdate_;
// Private Member Functions // Private Member Functions
//- Sample field on faces //- Sample volume field onto surface faces
template<class Type> template<class Type>
tmp<Field<Type>> sampleField tmp<Field<Type>> sampleOnFaces
( (
const GeometricField<Type, fvPatchField, volMesh>& vField const interpolation<Type>& sampler
) const; ) const;
//- Interpolate volume field onto surface points
template<class Type> template<class Type>
tmp<Field<Type>> tmp<Field<Type>> sampleOnPoints
interpolateField(const interpolation<Type>&) const; (
const interpolation<Type>& interpolator
) const;
public: public:
@ -168,78 +206,80 @@ public:
return cuttingPlane::Cf(); return cuttingPlane::Cf();
} }
//- For each face, the original cell in mesh
using cuttingPlane::meshCells;
//- For every face original cell in mesh
const labelList& meshCells() const
{
return cuttingPlane::meshCells();
}
//- Sample field on surface // Sample
//- Sample volume field onto surface faces
virtual tmp<scalarField> sample virtual tmp<scalarField> sample
( (
const volScalarField& const interpolation<scalar>& sampler
) const; ) const;
//- Sample volume field onto surface faces
//- Sample field on surface
virtual tmp<vectorField> sample virtual tmp<vectorField> sample
( (
const volVectorField& const interpolation<vector>& sampler
) const; ) const;
//- Sample field on surface //- Sample volume field onto surface faces
virtual tmp<sphericalTensorField> sample virtual tmp<sphericalTensorField> sample
( (
const volSphericalTensorField& const interpolation<sphericalTensor>& sampler
) const; ) const;
//- Sample field on surface //- Sample volume field onto surface faces
virtual tmp<symmTensorField> sample virtual tmp<symmTensorField> sample
( (
const volSymmTensorField& const interpolation<symmTensor>& sampler
) const; ) const;
//- Sample field on surface //- Sample volume field onto surface faces
virtual tmp<tensorField> sample virtual tmp<tensorField> sample
( (
const volTensorField& const interpolation<tensor>& sampler
) const; ) const;
//- Interpolate field on surface // Interpolate
//- Interpolate volume field onto surface points
virtual tmp<scalarField> interpolate virtual tmp<scalarField> interpolate
( (
const interpolation<scalar>& const interpolation<scalar>& interpolator
) const; ) const;
//- Interpolate volume field onto surface points
//- Interpolate field on surface
virtual tmp<vectorField> interpolate virtual tmp<vectorField> interpolate
( (
const interpolation<vector>& const interpolation<vector>& interpolator
) const; ) const;
//- Interpolate field on surface //- Interpolate volume field onto surface points
virtual tmp<sphericalTensorField> interpolate virtual tmp<sphericalTensorField> interpolate
( (
const interpolation<sphericalTensor>& const interpolation<sphericalTensor>& interpolator
) const; ) const;
//- Interpolate field on surface //- Interpolate volume field onto surface points
virtual tmp<symmTensorField> interpolate virtual tmp<symmTensorField> interpolate
( (
const interpolation<symmTensor>& const interpolation<symmTensor>& interpolator
) const; ) const;
//- Interpolate field on surface //- Interpolate volume field onto surface points
virtual tmp<tensorField> interpolate virtual tmp<tensorField> interpolate
( (
const interpolation<tensor>& const interpolation<tensor>& interpolator
) const; ) const;
//- Write
virtual void print(Ostream&) const; // Output
//- Print information
virtual void print(Ostream& os) const;
}; };

View File

@ -29,40 +29,50 @@ License
template<class Type> template<class Type>
Foam::tmp<Foam::Field<Type>> Foam::tmp<Foam::Field<Type>>
Foam::sampledPlane::sampleField Foam::sampledPlane::sampleOnFaces
( (
const GeometricField<Type, fvPatchField, volMesh>& vField const interpolation<Type>& sampler
) const ) const
{ {
return tmp<Field<Type>>::New(vField, meshCells()); return sampledSurface::sampleOnFaces
(
sampler,
meshCells(),
faces(),
points()
);
} }
template<class Type> template<class Type>
Foam::tmp<Foam::Field<Type>> Foam::tmp<Foam::Field<Type>>
Foam::sampledPlane::interpolateField Foam::sampledPlane::sampleOnPoints
( (
const interpolation<Type>& interpolator const interpolation<Type>& interpolator
) const ) const
{ {
// elements to sample
const labelList& elements = meshCells();
// One value per point. // One value per point.
// Initialize with Zero to handle missed/degenerate faces // Initialize with Zero to handle missed/degenerate faces
tmp<Field<Type>> tvalues(new Field<Type>(points().size(), Zero)); auto tvalues = tmp<Field<Type>>::New(points().size(), Zero);
Field<Type>& values = tvalues.ref(); auto& values = tvalues.ref();
boolList pointDone(points().size(), false); bitSet pointDone(points().size());
forAll(faces(), cutFacei) const faceList& fcs = faces();
forAll(fcs, facei)
{ {
const face& f = faces()[cutFacei]; const face& f = fcs[facei];
const label celli = meshCells()[cutFacei]; const label celli = elements[facei];
for (const label pointi : f) for (const label pointi : f)
{ {
if (!pointDone[pointi]) if (pointDone.set(pointi))
{ {
pointDone[pointi] = true;
values[pointi] = interpolator.interpolate values[pointi] = interpolator.interpolate
( (
points()[pointi], points()[pointi],

View File

@ -181,57 +181,6 @@ Foam::tmp<Foam::tensorField> Foam::sampledSurface::sample
} }
Foam::tmp<Foam::Field<Foam::scalar>>
Foam::sampledSurface::project(const Field<scalar>& field) const
{
tmp<Field<scalar>> tRes(new Field<scalar>(faces().size()));
Field<scalar>& res = tRes.ref();
forAll(faces(), facei)
{
res[facei] = field[facei];
}
return tRes;
}
Foam::tmp<Foam::Field<Foam::scalar>>
Foam::sampledSurface::project(const Field<vector>& field) const
{
tmp<Field<scalar>> tRes(new Field<scalar>(faces().size()));
project(tRes.ref(), field);
return tRes;
}
Foam::tmp<Foam::Field<Foam::vector>>
Foam::sampledSurface::project(const Field<sphericalTensor>& field) const
{
tmp<Field<vector>> tRes(new Field<vector>(faces().size()));
project(tRes.ref(), field);
return tRes;
}
Foam::tmp<Foam::Field<Foam::vector>>
Foam::sampledSurface::project(const Field<symmTensor>& field) const
{
tmp<Field<vector>> tRes(new Field<vector>(faces().size()));
project(tRes.ref(), field);
return tRes;
}
Foam::tmp<Foam::Field<Foam::vector>>
Foam::sampledSurface::project(const Field<tensor>& field) const
{
tmp<Field<vector>> tRes(new Field<vector>(faces().size()));
project(tRes.ref(), field);
return tRes;
}
void Foam::sampledSurface::print(Ostream& os) const void Foam::sampledSurface::print(Ostream& os) const
{ {
os << type(); os << type();
@ -240,7 +189,7 @@ void Foam::sampledSurface::print(Ostream& os) const
// * * * * * * * * * * * * * * * Friend Operators * * * * * * * * * * * * * // // * * * * * * * * * * * * * * * Friend Operators * * * * * * * * * * * * * //
Foam::Ostream& Foam::operator<<(Ostream &os, const sampledSurface& s) Foam::Ostream& Foam::operator<<(Ostream& os, const sampledSurface& s)
{ {
s.print(os); s.print(os);
os.check(FUNCTION_NAME); os.check(FUNCTION_NAME);

View File

@ -3,7 +3,7 @@
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration | \\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation \\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\/ M anipulation | Copyright (C) 2016 OpenCFD Ltd. \\/ M anipulation | Copyright (C) 2016-2018 OpenCFD Ltd.
------------------------------------------------------------------------------- -------------------------------------------------------------------------------
License License
This file is part of OpenFOAM. This file is part of OpenFOAM.
@ -70,11 +70,10 @@ SourceFiles
namespace Foam namespace Foam
{ {
// Forward declaration of friend functions and operators // Forward declarations
class sampledSurface; class sampledSurface;
Ostream& operator<<(Ostream& os, const sampledSurface& s);
Ostream& operator<<(Ostream&, const sampledSurface&);
/*---------------------------------------------------------------------------*\ /*---------------------------------------------------------------------------*\
@ -103,36 +102,28 @@ class sampledSurface
mutable scalar area_; mutable scalar area_;
// Service methods
//- Check field size matches surface size
template<class Type>
bool checkFieldSize(const Field<Type>&) const;
//- Project field onto surface
template<class ReturnType, class Type>
void project
(
Field<ReturnType>&,
const Field<Type>&
) const;
//- Project field onto surface
template<class ReturnType, class Type>
void project
(
Field<ReturnType>&,
const tmp<Field<Type>>&
) const;
//- Project field onto surface
template<class ReturnType, class Type>
tmp<Field<ReturnType>> project(const tmp<Field<Type>>&) const;
protected: protected:
// Protected Member functions // Protected Member Functions
//- General loop for sampling elements to faces
template<class Type>
static tmp<Field<Type>> sampleOnFaces
(
const interpolation<Type>& sampler,
const labelUList& elements,
const faceList& fcs,
const pointField& pts
);
//- Create cell values by averaging the point values
template<class Type>
static tmp<GeometricField<Type, fvPatchField, volMesh>> pointAverage
(
const GeometricField<Type, pointPatchField, pointMesh>& pfld
);
virtual void clearGeom() const; virtual void clearGeom() const;
@ -226,7 +217,7 @@ public:
// Member Functions // Member Functions
// Access // Access
//- Access to the underlying mesh //- Access to the underlying mesh
const polyMesh& mesh() const const polyMesh& mesh() const
@ -277,137 +268,100 @@ public:
scalar area() const; scalar area() const;
//- Integration of a field across the surface //- Sample volume field onto surface faces
template<class Type>
Type integrate(const Field<Type>&) const;
//- Integration of a field across the surface
template<class Type>
Type integrate(const tmp<Field<Type>>&) const;
//- Area-averaged value of a field across the surface
template<class Type>
Type average(const Field<Type>&) const;
//- Area-averaged value of a field across the surface
template<class Type>
Type average(const tmp<Field<Type>>&) const;
//- Project field onto surface
tmp<Field<scalar>> project(const Field<scalar>&) const;
//- Project field onto surface
tmp<Field<scalar>> project(const Field<vector>&) const;
//- Project field onto surface
tmp<Field<vector>> project(const Field<sphericalTensor>&) const;
//- Project field onto surface
tmp<Field<vector>> project(const Field<symmTensor>&) const;
//- Project field onto surface
tmp<Field<vector>> project(const Field<tensor>&) const;
//- Interpolate from points to cell centre
template<class Type>
tmp<GeometricField<Type, fvPatchField, volMesh>> pointAverage
(
const GeometricField<Type, pointPatchField, pointMesh>& pfld
) const;
//- Sample field on surface
virtual tmp<scalarField> sample virtual tmp<scalarField> sample
( (
const volScalarField& const interpolation<scalar>& sampler
) const = 0; ) const = 0;
//- Sample field on surface //- Sample volume field onto surface faces
virtual tmp<vectorField> sample virtual tmp<vectorField> sample
( (
const volVectorField& const interpolation<vector>& sampler
) const = 0; ) const = 0;
//- Sample field on surface //- Sample volume field onto surface faces
virtual tmp<sphericalTensorField> sample virtual tmp<sphericalTensorField> sample
( (
const volSphericalTensorField& const interpolation<sphericalTensor>& sampler
) const = 0; ) const = 0;
//- Sample field on surface //- Sample volume field onto surface faces
virtual tmp<symmTensorField> sample virtual tmp<symmTensorField> sample
( (
const volSymmTensorField& const interpolation<symmTensor>& sampler
) const = 0; ) const = 0;
//- Sample field on surface //- Sample volume field onto surface faces
virtual tmp<tensorField> sample virtual tmp<tensorField> sample
( (
const volTensorField& const interpolation<tensor>& sampler
) const = 0; ) const = 0;
//- Surface sample field on surface
//- Sample surface field onto surface
virtual tmp<scalarField> sample virtual tmp<scalarField> sample
( (
const surfaceScalarField& const surfaceScalarField& sField
) const; ) const;
//- Surface Sample field on surface //- Sample surface field onto surface
virtual tmp<vectorField> sample virtual tmp<vectorField> sample
( (
const surfaceVectorField& const surfaceVectorField& sField
) const; ) const;
//- Surface sample field on surface //- Sample surface field onto surface
virtual tmp<sphericalTensorField> sample virtual tmp<sphericalTensorField> sample
( (
const surfaceSphericalTensorField& const surfaceSphericalTensorField& sField
) const; ) const;
//- Surface sample field on surface //- Sample surface field onto surface
virtual tmp<symmTensorField> sample virtual tmp<symmTensorField> sample
( (
const surfaceSymmTensorField& const surfaceSymmTensorField& sField
) const; ) const;
//- Surface sample field on surface //- Sample surface field onto surface
virtual tmp<tensorField> sample virtual tmp<tensorField> sample
( (
const surfaceTensorField& const surfaceTensorField& sField
) const; ) const;
//- Interpolate field on surface
//- Interpolate volume field onto surface points
virtual tmp<scalarField> interpolate virtual tmp<scalarField> interpolate
( (
const interpolation<scalar>& const interpolation<scalar>& interpolator
) const = 0; ) const = 0;
//- Interpolate volume field onto surface points
//- Interpolate field on surface
virtual tmp<vectorField> interpolate virtual tmp<vectorField> interpolate
( (
const interpolation<vector>& const interpolation<vector>& interpolator
) const = 0; ) const = 0;
//- Interpolate field on surface //- Interpolate volume field onto surface points
virtual tmp<sphericalTensorField> interpolate virtual tmp<sphericalTensorField> interpolate
( (
const interpolation<sphericalTensor>& const interpolation<sphericalTensor>& interpolator
) const = 0; ) const = 0;
//- Interpolate field on surface //- Interpolate volume field onto surface points
virtual tmp<symmTensorField> interpolate virtual tmp<symmTensorField> interpolate
( (
const interpolation<symmTensor>& const interpolation<symmTensor>& interpolator
) const = 0; ) const = 0;
//- Interpolate field on surface //- Interpolate volume field onto surface points
virtual tmp<tensorField> interpolate virtual tmp<tensorField> interpolate
( (
const interpolation<tensor>& const interpolation<tensor>& interpolator
) const = 0; ) const = 0;
// Edit // Edit
//- Rename //- Rename
virtual void rename(const word& newName) virtual void rename(const word& newName)
@ -416,13 +370,13 @@ public:
} }
// Write // Write
//- Write //- Print information
virtual void print(Ostream&) const; virtual void print(Ostream& os) const;
//- Ostream operator //- Ostream operator
friend Ostream& operator<<(Ostream&, const sampledSurface&); friend Ostream& operator<<(Ostream& os, const sampledSurface& s);
}; };

View File

@ -3,7 +3,7 @@
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration | \\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation \\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\/ M anipulation | \\/ M anipulation | Copyright (C) 2018 OpenCFD Ltd.
------------------------------------------------------------------------------- -------------------------------------------------------------------------------
License License
This file is part of OpenFOAM. This file is part of OpenFOAM.
@ -25,129 +25,41 @@ License
#include "sampledSurface.H" #include "sampledSurface.H"
template<class Type> // * * * * * * * * * * * * Protected Member Functions * * * * * * * * * * * //
bool Foam::sampledSurface::checkFieldSize(const Field<Type>& field) const
{
if (faces().empty() || field.empty())
{
return false;
}
if (field.size() != faces().size()) template<class Type>
Foam::tmp<Foam::Field<Type>>
Foam::sampledSurface::sampleOnFaces
(
const interpolation<Type>& sampler,
const labelUList& elements,
const faceList& fcs,
const pointField& pts
)
{
const label len = elements.size();
if (len != fcs.size())
{ {
FatalErrorInFunction FatalErrorInFunction
<< "size mismatch: " << "size mismatch: "
<< "field (" << field.size() << "sampled elements (" << len
<< ") != surface (" << faces().size() << ")" << ") != faces (" << fcs.size() << ')'
<< exit(FatalError); << exit(FatalError);
} }
return true; auto tvalues = tmp<Field<Type>>::New(len);
} auto& values = tvalues.ref();
for (label i=0; i < len; ++i)
template<class Type>
Type Foam::sampledSurface::integrate(const Field<Type>& field) const
{
Type value = Zero;
if (checkFieldSize(field))
{ {
value = sum(field*magSf()); const label celli = elements[i];
const point pt = fcs[i].centre(pts);
values[i] = sampler.interpolate(pt, celli);
} }
reduce(value, sumOp<Type>()); return tvalues;
return value;
}
template<class Type>
Type Foam::sampledSurface::integrate(const tmp<Field<Type>>& field) const
{
Type value = integrate(field());
field.clear();
return value;
}
template<class Type>
Type Foam::sampledSurface::average(const Field<Type>& field) const
{
Type value = Zero;
if (checkFieldSize(field))
{
value = sum(field*magSf());
}
reduce(value, sumOp<Type>());
// avoid divide-by-zero
if (area())
{
return value/area();
}
else
{
return Zero;
}
}
template<class Type>
Type Foam::sampledSurface::average(const tmp<Field<Type>>& field) const
{
Type value = average(field());
field.clear();
return value;
}
template<class ReturnType, class Type>
void Foam::sampledSurface::project
(
Field<ReturnType>& res,
const Field<Type>& field
) const
{
if (checkFieldSize(field))
{
const vectorField& norm = Sf();
forAll(norm, facei)
{
res[facei] = field[facei] & (norm[facei]/mag(norm[facei]));
}
}
else
{
res.clear();
}
}
template<class ReturnType, class Type>
void Foam::sampledSurface::project
(
Field<ReturnType>& res,
const tmp<Field<Type>>& field
) const
{
project(res, field());
field.clear();
}
template<class ReturnType, class Type>
Foam::tmp<Foam::Field<ReturnType>>
Foam::sampledSurface::project
(
const tmp<Field<Type>>& field
) const
{
tmp<Field<ReturnType>> tRes(new Field<ReturnType>(faces().size()));
project(tRes(), field);
return tRes;
} }
@ -156,48 +68,45 @@ Foam::tmp<Foam::GeometricField<Type, Foam::fvPatchField, Foam::volMesh>>
Foam::sampledSurface::pointAverage Foam::sampledSurface::pointAverage
( (
const GeometricField<Type, pointPatchField, pointMesh>& pfld const GeometricField<Type, pointPatchField, pointMesh>& pfld
) const )
{ {
const fvMesh& mesh = dynamic_cast<const fvMesh&>(pfld.mesh()()); const fvMesh& mesh = dynamic_cast<const fvMesh&>(pfld.mesh()());
tmp<GeometricField<Type, fvPatchField, volMesh>> tcellAvg auto tcellAvg = tmp<GeometricField<Type, fvPatchField, volMesh>>::New
( (
new GeometricField<Type, fvPatchField, volMesh> IOobject
( (
IOobject "cellAvg",
( mesh.time().timeName(),
"cellAvg", pfld.db(),
mesh.time().timeName(), IOobject::NO_READ,
pfld.db(), IOobject::NO_WRITE,
IOobject::NO_READ, false
IOobject::NO_WRITE, ),
false mesh,
), dimensioned<Type>(dimless, Zero)
mesh,
dimensioned<Type>(dimless, Zero)
)
); );
GeometricField<Type, fvPatchField, volMesh>& cellAvg = tcellAvg.ref(); auto& cellAvg = tcellAvg.ref();
labelField nPointCells(mesh.nCells(), 0); labelField nPointCells(mesh.nCells(), Zero);
for (label pointi = 0; pointi < mesh.nPoints(); ++pointi)
{ {
for (label pointi = 0; pointi < mesh.nPoints(); pointi++) const Type& val = pfld[pointi];
const labelList& pCells = mesh.pointCells(pointi);
for (const label celli : pCells)
{ {
const labelList& pCells = mesh.pointCells(pointi); cellAvg[celli] += val;
++nPointCells[celli];
forAll(pCells, i)
{
label celli = pCells[i];
cellAvg[celli] += pfld[pointi];
nPointCells[celli]++;
}
} }
} }
forAll(cellAvg, celli) forAll(cellAvg, celli)
{ {
cellAvg[celli] /= nPointCells[celli]; cellAvg[celli] /= nPointCells[celli];
} }
// Give value to calculatedFvPatchFields // Give value to calculatedFvPatchFields
cellAvg.correctBoundaryConditions(); cellAvg.correctBoundaryConditions();

View File

@ -3,7 +3,7 @@
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration | \\ / O peration |
\\ / A nd | Copyright (C) 2011-2017 OpenFOAM Foundation \\ / A nd | Copyright (C) 2011-2017 OpenFOAM Foundation
\\/ M anipulation | Copyright (C) 2016 OpenCFD Ltd. \\/ M anipulation | Copyright (C) 2016-2018 OpenCFD Ltd.
------------------------------------------------------------------------------- -------------------------------------------------------------------------------
License License
This file is part of OpenFOAM. This file is part of OpenFOAM.
@ -28,6 +28,7 @@ License
#include "dictionary.H" #include "dictionary.H"
#include "Time.H" #include "Time.H"
#include "IOmanip.H" #include "IOmanip.H"
#include "interpolationCell.H"
#include "volPointInterpolation.H" #include "volPointInterpolation.H"
#include "PatchTools.H" #include "PatchTools.H"
#include "mapPolyMesh.H" #include "mapPolyMesh.H"
@ -61,19 +62,19 @@ void Foam::sampledSurfaces::writeGeometry() const
const fileName outputDir = outputPath_/time_.timeName(); const fileName outputDir = outputPath_/time_.timeName();
forAll(*this, surfI) forAll(*this, surfi)
{ {
const sampledSurface& s = operator[](surfI); const sampledSurface& s = operator[](surfi);
if (Pstream::parRun()) if (Pstream::parRun())
{ {
if (Pstream::master() && mergedList_[surfI].size()) if (Pstream::master() && mergedList_[surfi].size())
{ {
formatter_->write formatter_->write
( (
outputDir, outputDir,
s.name(), s.name(),
mergedList_[surfI] mergedList_[surfi]
); );
} }
} }
@ -90,9 +91,9 @@ void Foam::sampledSurfaces::writeOriginalIds()
const word fieldName = "Ids"; const word fieldName = "Ids";
const fileName outputDir = outputPath_/time_.timeName(); const fileName outputDir = outputPath_/time_.timeName();
forAll(*this, surfI) forAll(*this, surfi)
{ {
const sampledSurface& s = operator[](surfI); const sampledSurface& s = operator[](surfi);
if (isA<sampledTriSurfaceMesh>(s)) if (isA<sampledTriSurfaceMesh>(s))
{ {
@ -109,7 +110,7 @@ void Foam::sampledSurfaces::writeOriginalIds()
ids[i] = idLst[i]; ids[i] = idLst[i];
} }
writeSurface(ids, surfI, fieldName, outputDir); writeSurface(ids, surfi, fieldName, outputDir);
} }
} }
} }
@ -131,7 +132,8 @@ Foam::sampledSurfaces::sampledSurfaces
loadFromFiles_(false), loadFromFiles_(false),
outputPath_(fileName::null), outputPath_(fileName::null),
fieldSelection_(), fieldSelection_(),
interpolationScheme_(word::null), sampleFaceScheme_(word::null),
sampleNodeScheme_(word::null),
mergedList_(), mergedList_(),
formatter_(nullptr) formatter_(nullptr)
{ {
@ -143,8 +145,7 @@ Foam::sampledSurfaces::sampledSurfaces
{ {
outputPath_ = mesh_.time().path()/"postProcessing"/name; outputPath_ = mesh_.time().path()/"postProcessing"/name;
} }
// Remove ".." outputPath_.clean(); // Remove unneeded ".."
outputPath_.clean();
read(dict); read(dict);
} }
@ -164,7 +165,8 @@ Foam::sampledSurfaces::sampledSurfaces
loadFromFiles_(loadFromFiles), loadFromFiles_(loadFromFiles),
outputPath_(fileName::null), outputPath_(fileName::null),
fieldSelection_(), fieldSelection_(),
interpolationScheme_(word::null), sampleFaceScheme_(word::null),
sampleNodeScheme_(word::null),
mergedList_(), mergedList_(),
formatter_(nullptr) formatter_(nullptr)
{ {
@ -178,8 +180,7 @@ Foam::sampledSurfaces::sampledSurfaces
{ {
outputPath_ = time_.path()/"postProcessing"/name; outputPath_ = time_.path()/"postProcessing"/name;
} }
// Remove ".." outputPath_.clean(); // Remove unneeded ".."
outputPath_.clean();
read(dict); read(dict);
} }
@ -207,35 +208,38 @@ bool Foam::sampledSurfaces::execute()
bool Foam::sampledSurfaces::write() bool Foam::sampledSurfaces::write()
{ {
if (size()) if (empty())
{ {
// Finalize surfaces, merge points etc. return true;
update();
const label nFields = classifyFields();
// write geometry first if required,
// or when no fields would otherwise be written
if (nFields == 0 || formatter_->separateGeometry())
{
writeGeometry();
}
const IOobjectList objects(obr_, obr_.time().timeName());
sampleAndWrite<volScalarField>(objects);
sampleAndWrite<volVectorField>(objects);
sampleAndWrite<volSphericalTensorField>(objects);
sampleAndWrite<volSymmTensorField>(objects);
sampleAndWrite<volTensorField>(objects);
sampleAndWrite<surfaceScalarField>(objects);
sampleAndWrite<surfaceVectorField>(objects);
sampleAndWrite<surfaceSphericalTensorField>(objects);
sampleAndWrite<surfaceSymmTensorField>(objects);
sampleAndWrite<surfaceTensorField>(objects);
} }
// Finalize surfaces, merge points etc.
update();
const label nFields = classifyFields();
// write geometry first if required,
// or when no fields would otherwise be written
if (nFields == 0 || formatter_->separateGeometry())
{
writeGeometry();
}
const IOobjectList objects(obr_, obr_.time().timeName());
sampleAndWrite<volScalarField>(objects);
sampleAndWrite<volVectorField>(objects);
sampleAndWrite<volSphericalTensorField>(objects);
sampleAndWrite<volSymmTensorField>(objects);
sampleAndWrite<volTensorField>(objects);
sampleAndWrite<surfaceScalarField>(objects);
sampleAndWrite<surfaceVectorField>(objects);
sampleAndWrite<surfaceSphericalTensorField>(objects);
sampleAndWrite<surfaceSymmTensorField>(objects);
sampleAndWrite<surfaceTensorField>(objects);
return true; return true;
} }
@ -246,9 +250,12 @@ bool Foam::sampledSurfaces::read(const dictionary& dict)
if (surfacesFound) if (surfacesFound)
{ {
sampleFaceScheme_ = dict.lookupOrDefault<word>("sampleScheme", "cell");
dict.lookup("interpolationScheme") >> sampleNodeScheme_;
dict.lookup("fields") >> fieldSelection_; dict.lookup("fields") >> fieldSelection_;
dict.lookup("interpolationScheme") >> interpolationScheme_;
const word writeType(dict.lookup("surfaceFormat")); const word writeType(dict.lookup("surfaceFormat"));
// Define the surface formatter // Define the surface formatter
@ -277,9 +284,9 @@ bool Foam::sampledSurfaces::read(const dictionary& dict)
if (this->size()) if (this->size())
{ {
Info<< "Reading surface description:" << nl; Info<< "Reading surface description:" << nl;
forAll(*this, surfI) forAll(*this, surfi)
{ {
Info<< " " << operator[](surfI).name() << nl; Info<< " " << operator[](surfi).name() << nl;
} }
Info<< endl; Info<< endl;
} }
@ -290,9 +297,9 @@ bool Foam::sampledSurfaces::read(const dictionary& dict)
Pout<< "sample fields:" << fieldSelection_ << nl Pout<< "sample fields:" << fieldSelection_ << nl
<< "sample surfaces:" << nl << "(" << nl; << "sample surfaces:" << nl << "(" << nl;
forAll(*this, surfI) forAll(*this, surfi)
{ {
Pout<< " " << operator[](surfI) << endl; Pout<< " " << operator[](surfi) << nl;
} }
Pout<< ")" << endl; Pout<< ")" << endl;
} }
@ -332,9 +339,9 @@ void Foam::sampledSurfaces::readUpdate(const polyMesh::readUpdateState state)
bool Foam::sampledSurfaces::needsUpdate() const bool Foam::sampledSurfaces::needsUpdate() const
{ {
forAll(*this, surfI) forAll(*this, surfi)
{ {
if (operator[](surfI).needsUpdate()) if (operator[](surfi).needsUpdate())
{ {
return true; return true;
} }
@ -348,9 +355,9 @@ bool Foam::sampledSurfaces::expire()
{ {
bool justExpired = false; bool justExpired = false;
forAll(*this, surfI) forAll(*this, surfi)
{ {
if (operator[](surfI).expire()) if (operator[](surfi).expire())
{ {
justExpired = true; justExpired = true;
} }
@ -358,7 +365,7 @@ bool Foam::sampledSurfaces::expire()
// Clear merge information // Clear merge information
if (Pstream::parRun()) if (Pstream::parRun())
{ {
mergedList_[surfI].clear(); mergedList_[surfi].clear();
} }
} }
@ -379,9 +386,9 @@ bool Foam::sampledSurfaces::update()
// Serial: quick and easy, no merging required // Serial: quick and easy, no merging required
if (!Pstream::parRun()) if (!Pstream::parRun())
{ {
forAll(*this, surfI) forAll(*this, surfi)
{ {
if (operator[](surfI).update()) if (operator[](surfi).update())
{ {
updated = true; updated = true;
} }
@ -390,8 +397,9 @@ bool Foam::sampledSurfaces::update()
return updated; return updated;
} }
// Dimension as fraction of mesh bounding box // Dimension as fraction of mesh bounding box
scalar mergeDim = mergeTol_*mesh_.bounds().mag(); const scalar mergeDim = mergeTol_*mesh_.bounds().mag();
if (Pstream::master() && debug) if (Pstream::master() && debug)
{ {
@ -399,14 +407,14 @@ bool Foam::sampledSurfaces::update()
<< mergeDim << " metre" << endl; << mergeDim << " metre" << endl;
} }
forAll(*this, surfI) forAll(*this, surfi)
{ {
sampledSurface& s = operator[](surfI); sampledSurface& s = operator[](surfi);
if (s.update()) if (s.update())
{ {
updated = true; updated = true;
mergedList_[surfI].merge(s, mergeDim); mergedList_[surfi].merge(s, mergeDim);
} }
} }
@ -422,9 +430,9 @@ Foam::scalar Foam::sampledSurfaces::mergeTol()
Foam::scalar Foam::sampledSurfaces::mergeTol(const scalar tol) Foam::scalar Foam::sampledSurfaces::mergeTol(const scalar tol)
{ {
scalar oldTol = mergeTol_; const scalar prev(mergeTol_);
mergeTol_ = tol; mergeTol_ = tol;
return oldTol; return prev;
} }

View File

@ -44,13 +44,17 @@ Description
// Fields to be sampled // Fields to be sampled
fields (p U); fields (p U);
// Interpolation scheme to use (only used if interpolate=true for // Scheme to obtain face centre value
// the surfaces below) sampleScheme cell;
// Scheme to obtain node values
// (only used if interpolate=true for the surfaces below)
interpolationScheme cell; interpolationScheme cell;
// Output surface format // Output surface format
surfaceFormat vtk; surfaceFormat vtk;
formatOptions { } formatOptions { }
surfaces surfaces
( (
@ -95,7 +99,7 @@ SourceFiles
namespace Foam namespace Foam
{ {
// Forward declaration of classes // Forward declarations
class Time; class Time;
class fvMesh; class fvMesh;
class dictionary; class dictionary;
@ -130,25 +134,28 @@ class sampledSurfaces
fileName outputPath_; fileName outputPath_;
// Read from dictonary // Read from dictonary
//- Names of fields to sample //- Names of fields to sample
wordRes fieldSelection_; wordRes fieldSelection_;
//- Interpolation scheme to use //- Interpolation/sample scheme to obtain face values
word interpolationScheme_; word sampleFaceScheme_;
//- Interpolation/sample scheme to obtain node values
word sampleNodeScheme_;
// surfaces // Surfaces
//- Merged meshed surfaces (parallel only) //- Merged meshed surfaces (parallel only)
List<mergedSurf> mergedList_; List<mergedSurf> mergedList_;
// Calculated // Calculated
//- Surface formatter //- Surface formatter
autoPtr<surfaceWriter> formatter_; autoPtr<surfaceWriter> formatter_;
// Private Member Functions // Private Member Functions
@ -168,7 +175,7 @@ class sampledSurfaces
void writeSurface void writeSurface
( (
const Field<Type>& values, const Field<Type>& values,
const label surfI, const label surfi,
const word& fieldName, const word& fieldName,
const fileName& outputDir const fileName& outputDir
); );
@ -177,22 +184,25 @@ class sampledSurfaces
template<class Type> template<class Type>
void sampleAndWrite void sampleAndWrite
( (
const GeometricField<Type, fvPatchField, volMesh>& const GeometricField<Type, fvPatchField, volMesh>& vField
); );
//- Sample and write a particular surface field //- Sample and write a particular surface field
template<class Type> template<class Type>
void sampleAndWrite void sampleAndWrite
( (
const GeometricField<Type, fvsPatchField, surfaceMesh>& const GeometricField<Type, fvsPatchField, surfaceMesh>& sField
); );
//- Sample and write all sampled fields //- Sample and write all sampled fields
template<class Type> void sampleAndWrite(const IOobjectList& objects); template<class Type> void sampleAndWrite(const IOobjectList& objects);
//- Disallow default bitwise copy construct and assignment
sampledSurfaces(const sampledSurfaces&); //- No copy construct
void operator=(const sampledSurfaces&); sampledSurfaces(const sampledSurfaces&) = delete;
//- No copy assignment
void operator=(const sampledSurfaces&) = delete;
public: public:
@ -207,7 +217,7 @@ public:
sampledSurfaces sampledSurfaces
( (
const word& name, const word& name,
const Time& time, const Time& runTime,
const dictionary& dict const dictionary& dict
); );
@ -216,8 +226,8 @@ public:
sampledSurfaces sampledSurfaces
( (
const word& name, const word& name,
const objectRegistry&, const objectRegistry& obr,
const dictionary&, const dictionary& dict,
const bool loadFromFiles = false const bool loadFromFiles = false
); );
@ -265,7 +275,7 @@ public:
static scalar mergeTol(); static scalar mergeTol();
//- Set tolerance (and return old tolerance) //- Set tolerance (and return old tolerance)
static scalar mergeTol(const scalar); static scalar mergeTol(const scalar tol);
}; };

View File

@ -35,12 +35,12 @@ template<class Type>
void Foam::sampledSurfaces::writeSurface void Foam::sampledSurfaces::writeSurface
( (
const Field<Type>& values, const Field<Type>& values,
const label surfI, const label surfi,
const word& fieldName, const word& fieldName,
const fileName& outputDir const fileName& outputDir
) )
{ {
const sampledSurface& s = operator[](surfI); const sampledSurface& s = operator[](surfi);
if (Pstream::parRun()) if (Pstream::parRun())
{ {
@ -63,21 +63,21 @@ void Foam::sampledSurfaces::writeSurface
); );
// Renumber (point data) to correspond to merged points // Renumber (point data) to correspond to merged points
if (mergedList_[surfI].pointsMap().size() == allValues.size()) if (mergedList_[surfi].pointsMap().size() == allValues.size())
{ {
inplaceReorder(mergedList_[surfI].pointsMap(), allValues); inplaceReorder(mergedList_[surfi].pointsMap(), allValues);
allValues.setSize(mergedList_[surfI].points().size()); allValues.setSize(mergedList_[surfi].points().size());
} }
// Write to time directory under outputPath_ // Write to time directory under outputPath_
// skip surface without faces (eg, a failed cut-plane) // skip surface without faces (eg, a failed cut-plane)
if (mergedList_[surfI].size()) if (mergedList_[surfi].size())
{ {
sampleFile = formatter_->write sampleFile = formatter_->write
( (
outputDir, outputDir,
s.name(), s.name(),
mergedList_[surfI], mergedList_[surfi],
fieldName, fieldName,
allValues, allValues,
s.interpolate() s.interpolate()
@ -123,37 +123,46 @@ void Foam::sampledSurfaces::sampleAndWrite
const GeometricField<Type, fvPatchField, volMesh>& vField const GeometricField<Type, fvPatchField, volMesh>& vField
) )
{ {
// interpolator for this field // sampler/interpolator for this field
autoPtr<interpolation<Type>> interpolatorPtr; autoPtr<interpolation<Type>> interpPtr;
const word& fieldName = vField.name(); const word& fieldName = vField.name();
const fileName outputDir = outputPath_/vField.time().timeName(); const fileName outputDir = outputPath_/vField.time().timeName();
forAll(*this, surfI) forAll(*this, surfi)
{ {
const sampledSurface& s = operator[](surfI); const sampledSurface& s = operator[](surfi);
Field<Type> values; Field<Type> values;
if (s.interpolate()) if (s.interpolate())
{ {
if (interpolatorPtr.empty()) if (interpPtr.empty())
{ {
interpolatorPtr = interpolation<Type>::New interpPtr = interpolation<Type>::New
( (
interpolationScheme_, sampleNodeScheme_,
vField vField
); );
} }
values = s.interpolate(interpolatorPtr()); values = s.interpolate(*interpPtr);
} }
else else
{ {
values = s.sample(vField); if (interpPtr.empty())
{
interpPtr = interpolation<Type>::New
(
sampleFaceScheme_,
vField
);
}
values = s.sample(*interpPtr);
} }
writeSurface<Type>(values, surfI, fieldName, outputDir); writeSurface<Type>(values, surfi, fieldName, outputDir);
} }
} }
@ -167,11 +176,11 @@ void Foam::sampledSurfaces::sampleAndWrite
const word& fieldName = sField.name(); const word& fieldName = sField.name();
const fileName outputDir = outputPath_/sField.time().timeName(); const fileName outputDir = outputPath_/sField.time().timeName();
forAll(*this, surfI) forAll(*this, surfi)
{ {
const sampledSurface& s = operator[](surfI); const sampledSurface& s = operator[](surfi);
Field<Type> values(s.sample(sField)); Field<Type> values(s.sample(sField));
writeSurface<Type>(values, surfI, fieldName, outputDir); writeSurface<Type>(values, surfi, fieldName, outputDir);
} }
} }
@ -191,13 +200,11 @@ void Foam::sampledSurfaces::sampleAndWrite(const IOobjectList& objects)
writeOriginalIds(); writeOriginalIds();
} }
forAll(fieldNames, fieldi) for (const word& fieldName : fieldNames)
{ {
const word& fieldName = fieldNames[fieldi]; if (verbose_)
if ((Pstream::master()) && verbose_)
{ {
Pout<< "sampleAndWrite: " << fieldName << endl; Info<< "sampleAndWrite: " << fieldName << endl;
} }
if (loadFromFiles_) if (loadFromFiles_)

View File

@ -87,9 +87,8 @@ void Foam::sampledTriSurfaceMesh::setZoneMap
) )
{ {
label sz = 0; label sz = 0;
forAll(zoneLst, zonei) for (const surfZone& zn : zoneLst)
{ {
const surfZone& zn = zoneLst[zonei];
sz += zn.size(); sz += zn.size();
} }
@ -119,9 +118,8 @@ Foam::sampledTriSurfaceMesh::nonCoupledboundaryTree() const
labelList bndFaces(mesh().nFaces()-mesh().nInternalFaces()); labelList bndFaces(mesh().nFaces()-mesh().nInternalFaces());
label bndI = 0; label bndI = 0;
forAll(patches, patchi) for (const polyPatch& pp : patches)
{ {
const polyPatch& pp = patches[patchi];
if (!pp.coupled()) if (!pp.coupled())
{ {
forAll(pp, i) forAll(pp, i)
@ -174,10 +172,10 @@ bool Foam::sampledTriSurfaceMesh::update(const meshSearch& meshSearcher)
// elements // elements
globalIndex globalCells(onBoundary() ? mesh().nFaces() : mesh().nCells()); globalIndex globalCells(onBoundary() ? mesh().nFaces() : mesh().nCells());
forAll(nearest, i) for (nearInfo& near : nearest)
{ {
nearest[i].first() = GREAT; near.first() = GREAT;
nearest[i].second() = labelMax; near.second() = labelMax;
} }
if (sampleSource_ == cells) if (sampleSource_ == cells)
@ -333,20 +331,16 @@ bool Foam::sampledTriSurfaceMesh::update(const meshSearch& meshSearcher)
const triSurface::FaceType& f = s[facei]; const triSurface::FaceType& f = s[facei];
const label regionid = f.region(); const label regionid = f.region();
Map<label>::iterator fnd = zoneSizes.find(regionid); auto fnd = zoneSizes.find(regionid);
if (fnd != zoneSizes.end()) if (fnd.found())
{ {
fnd()++; ++(*fnd);
} }
else else
{ {
// This shouldn't happen // This shouldn't happen
zoneSizes.insert(regionid, 1); zoneSizes.insert(regionid, 1);
zoneNames.set zoneNames.set(regionid, word::printf("patch%d", regionid));
(
regionid,
word::printf("patch%d", regionid)
);
} }
// Store new faces compact // Store new faces compact
@ -355,14 +349,12 @@ bool Foam::sampledTriSurfaceMesh::update(const meshSearch& meshSearcher)
++newFacei; ++newFacei;
// Renumber face points // Renumber face points
forAll(f, fp) for (const label labi : f)
{ {
const label labI = f[fp]; if (reversePointMap[labi] == -1)
if (reversePointMap[labI] == -1)
{ {
pointMap[newPointi] = labI; pointMap[newPointi] = labi;
reversePointMap[labI] = newPointi++; reversePointMap[labi] = newPointi++;
} }
} }
} }
@ -380,16 +372,16 @@ bool Foam::sampledTriSurfaceMesh::update(const meshSearch& meshSearcher)
surfZoneList zoneLst(zoneSizes.size()); surfZoneList zoneLst(zoneSizes.size());
label start = 0; label start = 0;
label zoneI = 0; label zoneI = 0;
forAllIter(Map<label>, zoneSizes, iter) forAllIters(zoneSizes, iter)
{ {
// No negative regionids, so Map<label> sorts properly // No negative regionids, so Map<label> usually sorts properly
const label regionid = iter.key(); const label regionid = iter.key();
word name; word name;
Map<word>::const_iterator fnd = zoneNames.find(regionid); auto fnd = zoneNames.cfind(regionid);
if (fnd != zoneNames.end()) if (fnd.found())
{ {
name = fnd(); name = *fnd;
} }
if (name.empty()) if (name.empty())
{ {
@ -420,7 +412,7 @@ bool Foam::sampledTriSurfaceMesh::update(const meshSearch& meshSearcher)
forAll(zoneIds_, facei) forAll(zoneIds_, facei)
{ {
label zonei = zoneIds_[facei]; const label zonei = zoneIds_[facei];
label sortedFacei = zoneLst[zonei].start() + zoneLst[zonei].size()++; label sortedFacei = zoneLst[zonei].start() + zoneLst[zonei].size()++;
sortedFaceMap[sortedFacei] = faceMap[facei]; sortedFaceMap[sortedFacei] = faceMap[facei];
} }
@ -460,9 +452,9 @@ bool Foam::sampledTriSurfaceMesh::update(const meshSearch& meshSearcher)
reversePointMap[origF[2]] reversePointMap[origF[2]]
); );
forAll(f, fp) for (const label labi : f)
{ {
pointToFace[f[fp]] = facei; pointToFace[labi] = facei;
} }
} }
@ -658,8 +650,8 @@ Foam::sampledTriSurfaceMesh::sampledTriSurfaceMesh
keepIds_(false), keepIds_(false),
originalIds_(), originalIds_(),
zoneIds_(), zoneIds_(),
sampleElements_(0), sampleElements_(),
samplePoints_(0) samplePoints_()
{} {}
@ -691,8 +683,8 @@ Foam::sampledTriSurfaceMesh::sampledTriSurfaceMesh
keepIds_(dict.lookupOrDefault("keepIds", false)), keepIds_(dict.lookupOrDefault("keepIds", false)),
originalIds_(), originalIds_(),
zoneIds_(), zoneIds_(),
sampleElements_(0), sampleElements_(),
samplePoints_(0) samplePoints_()
{} {}
@ -725,8 +717,8 @@ Foam::sampledTriSurfaceMesh::sampledTriSurfaceMesh
keepIds_(false), keepIds_(false),
originalIds_(), originalIds_(),
zoneIds_(), zoneIds_(),
sampleElements_(0), sampleElements_(),
samplePoints_(0) samplePoints_()
{} {}
@ -832,45 +824,46 @@ bool Foam::sampledTriSurfaceMesh::update(const treeBoundBox& bb)
Foam::tmp<Foam::scalarField> Foam::sampledTriSurfaceMesh::sample Foam::tmp<Foam::scalarField> Foam::sampledTriSurfaceMesh::sample
( (
const volScalarField& vField const interpolation<scalar>& sampler
) const ) const
{ {
return sampleField(vField); return sampleOnFaces(sampler);
} }
Foam::tmp<Foam::vectorField> Foam::sampledTriSurfaceMesh::sample Foam::tmp<Foam::vectorField> Foam::sampledTriSurfaceMesh::sample
( (
const volVectorField& vField const interpolation<vector>& sampler
) const ) const
{ {
return sampleField(vField); return sampleOnFaces(sampler);
} }
Foam::tmp<Foam::sphericalTensorField> Foam::sampledTriSurfaceMesh::sample Foam::tmp<Foam::sphericalTensorField> Foam::sampledTriSurfaceMesh::sample
( (
const volSphericalTensorField& vField const interpolation<sphericalTensor>& sampler
) const ) const
{ {
return sampleField(vField); return sampleOnFaces(sampler);
} }
Foam::tmp<Foam::symmTensorField> Foam::sampledTriSurfaceMesh::sample Foam::tmp<Foam::symmTensorField> Foam::sampledTriSurfaceMesh::sample
( (
const volSymmTensorField& vField const interpolation<symmTensor>& sampler
) const ) const
{ {
return sampleField(vField); return sampleOnFaces(sampler);
} }
Foam::tmp<Foam::tensorField> Foam::sampledTriSurfaceMesh::sample Foam::tmp<Foam::tensorField> Foam::sampledTriSurfaceMesh::sample
( (
const volTensorField& vField const interpolation<tensor>& sampler
) const ) const
{ {
return sampleField(vField); return sampleOnFaces(sampler);
} }
@ -879,7 +872,7 @@ Foam::tmp<Foam::scalarField> Foam::sampledTriSurfaceMesh::interpolate
const interpolation<scalar>& interpolator const interpolation<scalar>& interpolator
) const ) const
{ {
return interpolateField(interpolator); return sampleOnPoints(interpolator);
} }
@ -888,7 +881,7 @@ Foam::tmp<Foam::vectorField> Foam::sampledTriSurfaceMesh::interpolate
const interpolation<vector>& interpolator const interpolation<vector>& interpolator
) const ) const
{ {
return interpolateField(interpolator); return sampleOnPoints(interpolator);
} }
Foam::tmp<Foam::sphericalTensorField> Foam::sampledTriSurfaceMesh::interpolate Foam::tmp<Foam::sphericalTensorField> Foam::sampledTriSurfaceMesh::interpolate
@ -896,7 +889,7 @@ Foam::tmp<Foam::sphericalTensorField> Foam::sampledTriSurfaceMesh::interpolate
const interpolation<sphericalTensor>& interpolator const interpolation<sphericalTensor>& interpolator
) const ) const
{ {
return interpolateField(interpolator); return sampleOnPoints(interpolator);
} }
@ -905,7 +898,7 @@ Foam::tmp<Foam::symmTensorField> Foam::sampledTriSurfaceMesh::interpolate
const interpolation<symmTensor>& interpolator const interpolation<symmTensor>& interpolator
) const ) const
{ {
return interpolateField(interpolator); return sampleOnPoints(interpolator);
} }
@ -914,7 +907,7 @@ Foam::tmp<Foam::tensorField> Foam::sampledTriSurfaceMesh::interpolate
const interpolation<tensor>& interpolator const interpolation<tensor>& interpolator
) const ) const
{ {
return interpolateField(interpolator); return sampleOnPoints(interpolator);
} }

View File

@ -3,7 +3,7 @@
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration | \\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation \\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\/ M anipulation | Copyright (C) 2016 OpenCFD Ltd. \\/ M anipulation | Copyright (C) 2016-2018 OpenCFD Ltd.
------------------------------------------------------------------------------- -------------------------------------------------------------------------------
License License
This file is part of OpenFOAM. This file is part of OpenFOAM.
@ -60,6 +60,31 @@ Description
to be on one processor only. So after stitching (by sampledSurfaces) to be on one processor only. So after stitching (by sampledSurfaces)
the original surface should be complete. the original surface should be complete.
This is often embedded as part of a sampled surfaces function object.
Usage
Example of function object partial specification:
\verbatim
surfaces
(
surface1
{
type sampledTriSurfaceMesh;
surface something.obj;
source cells;
}
);
\endverbatim
Where the sub-entries comprise:
\table
Property | Description | Required | Default
type | sampledTriSurfaceMesh | yes |
surface | surface name in triSurface/ | yes |
source | cells/insideCells/boundaryFaces | yes |
keepIds | pass through id numbering | no | false
\endtable
SourceFiles SourceFiles
sampledTriSurfaceMesh.C sampledTriSurfaceMesh.C
sampledTriSurfaceMeshTemplates.C sampledTriSurfaceMeshTemplates.C
@ -144,17 +169,19 @@ private:
//- Get tree of all non-coupled boundary faces //- Get tree of all non-coupled boundary faces
const indexedOctree<treeDataFace>& nonCoupledboundaryTree() const; const indexedOctree<treeDataFace>& nonCoupledboundaryTree() const;
//- Sample field on faces //- Sample volume field onto surface faces
template<class Type> template<class Type>
tmp<Field<Type>> sampleField tmp<Field<Type>> sampleOnFaces
( (
const GeometricField<Type, fvPatchField, volMesh>& vField const interpolation<Type>& sampler
) const; ) const;
//- Interpolate volume field onto surface points
template<class Type> template<class Type>
tmp<Field<Type>> tmp<Field<Type>> sampleOnPoints
interpolateField(const interpolation<Type>&) const; (
const interpolation<Type>& interpolator
) const;
bool update(const meshSearch& meshSearcher); bool update(const meshSearch& meshSearcher);
@ -200,7 +227,11 @@ public:
// Member Functions // Member Functions
//- Set new zoneIds list based on the surfZoneList information //- Set new zoneIds list based on the surfZoneList information
static void setZoneMap(const surfZoneList&, labelList& zoneIds); static void setZoneMap
(
const surfZoneList& zoneLst,
labelList& zoneIds
);
//- Does the surface need an update? //- Does the surface need an update?
@ -218,7 +249,7 @@ public:
//- Update the surface using a bound box to limit the searching. //- Update the surface using a bound box to limit the searching.
// For direct use, i.e. not through sample. // For direct use, i.e. not through sample.
// Do nothing (and return false) if no update was needed // Do nothing (and return false) if no update was needed
bool update(const treeBoundBox&); bool update(const treeBoundBox& bb);
//- Points of surface //- Points of surface
virtual const pointField& points() const virtual const pointField& points() const
@ -276,70 +307,76 @@ public:
} }
//- Sample field on surface // Sample
//- Sample volume field onto surface faces
virtual tmp<scalarField> sample virtual tmp<scalarField> sample
( (
const volScalarField& const interpolation<scalar>& sampler
) const; ) const;
//- Sample field on surface //- Sample volume field onto surface faces
virtual tmp<vectorField> sample virtual tmp<vectorField> sample
( (
const volVectorField& const interpolation<vector>& sampler
) const; ) const;
//- Sample field on surface //- Sample volume field onto surface faces
virtual tmp<sphericalTensorField> sample virtual tmp<sphericalTensorField> sample
( (
const volSphericalTensorField& const interpolation<sphericalTensor>& sampler
) const; ) const;
//- Sample field on surface //- Sample volume field onto surface faces
virtual tmp<symmTensorField> sample virtual tmp<symmTensorField> sample
( (
const volSymmTensorField& const interpolation<symmTensor>& sampler
) const; ) const;
//- Sample field on surface //- Sample volume field onto surface faces
virtual tmp<tensorField> sample virtual tmp<tensorField> sample
( (
const volTensorField& const interpolation<tensor>& sampler
) const; ) const;
//- Interpolate field on surface // Interpolate
//- Interpolate volume field onto surface points
virtual tmp<scalarField> interpolate virtual tmp<scalarField> interpolate
( (
const interpolation<scalar>& const interpolation<scalar>& interpolator
) const; ) const;
//- Interpolate volume field onto surface points
//- Interpolate field on surface
virtual tmp<vectorField> interpolate virtual tmp<vectorField> interpolate
( (
const interpolation<vector>& const interpolation<vector>& interpolator
) const; ) const;
//- Interpolate field on surface //- Interpolate volume field onto surface points
virtual tmp<sphericalTensorField> interpolate virtual tmp<sphericalTensorField> interpolate
( (
const interpolation<sphericalTensor>& const interpolation<sphericalTensor>& interpolator
) const; ) const;
//- Interpolate field on surface //- Interpolate volume field onto surface points
virtual tmp<symmTensorField> interpolate virtual tmp<symmTensorField> interpolate
( (
const interpolation<symmTensor>& const interpolation<symmTensor>& interpolator
) const; ) const;
//- Interpolate field on surface //- Interpolate volume field onto surface points
virtual tmp<tensorField> interpolate virtual tmp<tensorField> interpolate
( (
const interpolation<tensor>& const interpolation<tensor>& interpolator
) const; ) const;
//- Write information
virtual void print(Ostream&) const; // Output
//- Write
virtual void print(Ostream& os) const;
}; };

View File

@ -2,7 +2,7 @@
========= | ========= |
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration | \\ / O peration |
\\ / A nd | Copyright (C) 2017 OpenCFD Ltd. \\ / A nd | Copyright (C) 2017-2018 OpenCFD Ltd.
\\/ M anipulation | \\/ M anipulation |
------------------------------------------------------------------------------- -------------------------------------------------------------------------------
License License
@ -77,28 +77,24 @@ Foam::sampledTriSurfaceMeshNormal::sampledTriSurfaceMeshNormal
{} {}
// * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * //
Foam::sampledTriSurfaceMeshNormal::~sampledTriSurfaceMeshNormal()
{}
// * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * // // * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
Foam::tmp<Foam::Field<Foam::vector>> Foam::tmp<Foam::Field<Foam::vector>>
Foam::sampledTriSurfaceMeshNormal::sample Foam::sampledTriSurfaceMeshNormal::sample
( (
const GeometricField<vector, fvPatchField, volMesh>& vField const interpolation<vector>& sampler
) const ) const
{ {
tmp<Field<vector>> tfld(new Field<vector>(size(), vector::zero)); auto tvalues = tmp<Field<vector>>::New(size(), Zero);
tfld.ref().replace
tvalues.ref().replace
( (
0, 0,
meshedSurface::faceNormals() meshedSurface::faceNormals()
&sampledTriSurfaceMesh::sample(vField) &sampledTriSurfaceMesh::sample(sampler)
); );
return tfld;
return tvalues;
} }
@ -108,26 +104,19 @@ Foam::sampledTriSurfaceMeshNormal::interpolate
const interpolation<vector>& interpolator const interpolation<vector>& interpolator
) const ) const
{ {
// One value per vertex auto tvalues = tmp<Field<vector>>::New(points().size(), Zero);
tmp<vectorField> tn
(
new vectorField
(
points().size(),
vector::zero
)
);
pointField allNormals(tn().size(), vector::zero); pointField allNormals(points().size(), Zero);
UIndirectList<vector>(allNormals, meshPoints()) = pointNormals(); UIndirectList<vector>(allNormals, meshPoints()) = pointNormals();
tn.ref().replace tvalues.ref().replace
( (
0, 0,
allNormals allNormals
&sampledTriSurfaceMesh::interpolate(interpolator) &sampledTriSurfaceMesh::interpolate(interpolator)
); );
return tn;
return tvalues;
} }

View File

@ -2,7 +2,7 @@
========= | ========= |
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration | \\ / O peration |
\\ / A nd | Copyright (C) 2017 OpenCFD Ltd. \\ / A nd | Copyright (C) 2017-2018 OpenCFD Ltd.
\\/ M anipulation | \\/ M anipulation |
------------------------------------------------------------------------------- -------------------------------------------------------------------------------
License License
@ -31,6 +31,34 @@ Description
Returns a vector field with the value in the first component and sets Returns a vector field with the value in the first component and sets
the other two to zero. the other two to zero.
This is often embedded as part of a sampled surfaces function object.
Usage
Example of function object partial specification:
\verbatim
surfaces
(
surface1
{
type sampledTriSurfaceMeshNormal;
surface something.obj;
source cells;
}
);
\endverbatim
Where the sub-entries comprise:
\table
Property | Description | Required | Default
type | sampledTriSurfaceMeshNormal | yes |
surface | surface name in triSurface/ | yes |
source | cells/insideCells/boundaryFaces | yes |
keepIds | pass through id numbering | no | false
\endtable
SeeAlso
Foam::sampledTriSurfaceMesh
SourceFiles SourceFiles
sampledTriSurfaceMeshNormal.C sampledTriSurfaceMeshNormal.C
sampledTriSurfaceMeshNormalTemplates.C sampledTriSurfaceMeshNormalTemplates.C
@ -91,97 +119,102 @@ public:
//- Destructor //- Destructor
virtual ~sampledTriSurfaceMeshNormal(); virtual ~sampledTriSurfaceMeshNormal() = default;
// Member Functions // Member Functions
//- Sample field on surface // Sample
//- Sample volume field onto surface faces
virtual tmp<scalarField> sample virtual tmp<scalarField> sample
( (
const volScalarField& const interpolation<scalar>& sampler
) const ) const
{ {
NotImplemented; NotImplemented;
return nullptr; return nullptr;
} }
//- Sample field on surface //- Sample volume field onto surface faces
virtual tmp<vectorField> sample virtual tmp<vectorField> sample
( (
const volVectorField& const interpolation<vector>& sampler
) const; ) const;
//- Sample field on surface //- Sample volume field onto surface faces
virtual tmp<sphericalTensorField> sample virtual tmp<sphericalTensorField> sample
( (
const volSphericalTensorField& const interpolation<sphericalTensor>& sampler
) const ) const
{ {
NotImplemented; NotImplemented;
return nullptr; return nullptr;
} }
//- Sample field on surface //- Sample volume field onto surface faces
virtual tmp<symmTensorField> sample virtual tmp<symmTensorField> sample
( (
const volSymmTensorField& const interpolation<symmTensor>& sampler
) const ) const
{ {
NotImplemented; NotImplemented;
return nullptr; return nullptr;
} }
//- Sample field on surface //- Sample volume field onto surface faces
virtual tmp<tensorField> sample virtual tmp<tensorField> sample
( (
const volTensorField& const interpolation<tensor>& sampler
) const ) const
{ {
NotImplemented; NotImplemented;
return nullptr; return nullptr;
} }
//- Interpolate field on surface
// Interpolate
//- Interpolate volume field onto surface points
virtual tmp<scalarField> interpolate virtual tmp<scalarField> interpolate
( (
const interpolation<scalar>& const interpolation<scalar>& interpolator
) const ) const
{ {
NotImplemented; NotImplemented;
return nullptr; return nullptr;
} }
//- Interpolate field on surface //- Interpolate volume field onto surface points
virtual tmp<vectorField> interpolate virtual tmp<vectorField> interpolate
( (
const interpolation<vector>& const interpolation<vector>& interpolator
) const; ) const;
//- Interpolate field on surface //- Interpolate volume field onto surface points
virtual tmp<sphericalTensorField> interpolate virtual tmp<sphericalTensorField> interpolate
( (
const interpolation<sphericalTensor>& const interpolation<sphericalTensor>& interpolator
) const ) const
{ {
NotImplemented; NotImplemented;
return nullptr; return nullptr;
} }
//- Interpolate field on surface //- Interpolate volume field onto surface points
virtual tmp<symmTensorField> interpolate virtual tmp<symmTensorField> interpolate
( (
const interpolation<symmTensor>& const interpolation<symmTensor>& interpolator
) const ) const
{ {
NotImplemented; NotImplemented;
return nullptr; return nullptr;
} }
//- Interpolate field on surface //- Interpolate volume field onto surface points
virtual tmp<tensorField> interpolate virtual tmp<tensorField> interpolate
( (
const interpolation<tensor>& const interpolation<tensor>& interpolator
) const ) const
{ {
NotImplemented; NotImplemented;

View File

@ -3,7 +3,7 @@
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration | \\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation \\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\/ M anipulation | Copyright (C) 2016 OpenCFD Ltd. \\/ M anipulation | Copyright (C) 2016-2018 OpenCFD Ltd.
------------------------------------------------------------------------------- -------------------------------------------------------------------------------
License License
This file is part of OpenFOAM. This file is part of OpenFOAM.
@ -29,54 +29,61 @@ License
template<class Type> template<class Type>
Foam::tmp<Foam::Field<Type>> Foam::tmp<Foam::Field<Type>>
Foam::sampledTriSurfaceMesh::sampleField Foam::sampledTriSurfaceMesh::sampleOnFaces
( (
const GeometricField<Type, fvPatchField, volMesh>& vField const interpolation<Type>& sampler
) const ) const
{ {
// One value per face const labelList& elements = sampleElements_;
tmp<Field<Type>> tvalues(new Field<Type>(sampleElements_.size()));
Field<Type>& values = tvalues.ref();
if (!onBoundary()) if (!onBoundary())
{ {
// Sample cells // Sample cells
forAll(sampleElements_, triI) return sampledSurface::sampleOnFaces
{ (
values[triI] = vField[sampleElements_[triI]]; sampler,
} elements,
faces(),
points()
);
} }
else
//
// Sample boundary faces
//
auto tvalues = tmp<Field<Type>>::New(elements.size());
auto& values = tvalues.ref();
const polyBoundaryMesh& pbm = mesh().boundaryMesh();
// Create flat boundary field
const label nBnd = mesh().nFaces()-mesh().nInternalFaces();
Field<Type> bVals(nBnd, Zero);
const auto& bField = sampler.psi().boundaryField();
forAll(bField, patchi)
{ {
// Sample boundary faces const label bFacei = (pbm[patchi].start() - mesh().nInternalFaces());
const polyBoundaryMesh& pbm = mesh().boundaryMesh(); SubList<Type>
const label nBnd = mesh().nFaces()-mesh().nInternalFaces(); (
bVals,
bField[patchi].size(),
bFacei
) = bField[patchi];
}
// Create flat boundary field // Sample in flat boundary field
Field<Type> bVals(nBnd, Zero); forAll(elements, i)
{
forAll(vField.boundaryField(), patchi) const label bFacei = (elements[i] - mesh().nInternalFaces());
{ values[i] = bVals[bFacei];
label bFacei = pbm[patchi].start() - mesh().nInternalFaces();
SubList<Type>
(
bVals,
vField.boundaryField()[patchi].size(),
bFacei
) = vField.boundaryField()[patchi];
}
// Sample in flat boundary field
forAll(sampleElements_, triI)
{
label facei = sampleElements_[triI];
values[triI] = bVals[facei-mesh().nInternalFaces()];
}
} }
return tvalues; return tvalues;
@ -85,18 +92,18 @@ Foam::sampledTriSurfaceMesh::sampleField
template<class Type> template<class Type>
Foam::tmp<Foam::Field<Type>> Foam::tmp<Foam::Field<Type>>
Foam::sampledTriSurfaceMesh::interpolateField Foam::sampledTriSurfaceMesh::sampleOnPoints
( (
const interpolation<Type>& interpolator const interpolation<Type>& interpolator
) const ) const
{ {
// One value per vertex // One value per vertex
tmp<Field<Type>> tvalues(new Field<Type>(sampleElements_.size())); auto tvalues = tmp<Field<Type>>::New(sampleElements_.size());
Field<Type>& values = tvalues.ref(); auto& values = tvalues.ref();
if (!onBoundary()) if (!onBoundary())
{ {
// Sample cells. // Sample cells
forAll(sampleElements_, pointi) forAll(sampleElements_, pointi)
{ {
@ -109,11 +116,11 @@ Foam::sampledTriSurfaceMesh::interpolateField
} }
else else
{ {
// Sample boundary faces. // Sample boundary faces
forAll(samplePoints_, pointi) forAll(samplePoints_, pointi)
{ {
label facei = sampleElements_[pointi]; const label facei = sampleElements_[pointi];
values[pointi] = interpolator.interpolate values[pointi] = interpolator.interpolate
( (

View File

@ -3,7 +3,7 @@
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration | \\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation \\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\/ M anipulation | \\/ M anipulation | Copyright (C) 2018 OpenCFD Ltd.
------------------------------------------------------------------------------- -------------------------------------------------------------------------------
License License
This file is part of OpenFOAM. This file is part of OpenFOAM.
@ -59,53 +59,48 @@ bool Foam::sampledThresholdCellFaces::updateGeometry() const
prevTimeIndex_ = fvm.time().timeIndex(); prevTimeIndex_ = fvm.time().timeIndex();
// Optionally read volScalarField // Use volField from database, or try to read it in
autoPtr<volScalarField> readFieldPtr_;
// 1. see if field in database const auto* cellFldPtr = fvm.lookupObjectPtr<volScalarField>(fieldName_);
// 2. see if field can be read
const volScalarField* cellFldPtr = nullptr; if (debug)
if (fvm.foundObject<volScalarField>(fieldName_))
{ {
if (debug) if (cellFldPtr)
{ {
InfoInFunction<< "Lookup " << fieldName_ << endl; InfoInFunction << "Lookup " << fieldName_ << endl;
} }
else
cellFldPtr = &fvm.lookupObject<volScalarField>(fieldName_);
}
else
{
// Bit of a hack. Read field and store.
if (debug)
{ {
InfoInFunction InfoInFunction
<< "Reading " << fieldName_ << "Reading " << fieldName_
<< " from time " << fvm.time().timeName() << " from time " << fvm.time().timeName()
<< endl; << endl;
} }
readFieldPtr_.reset
(
new volScalarField
(
IOobject
(
fieldName_,
fvm.time().timeName(),
fvm,
IOobject::MUST_READ,
IOobject::NO_WRITE,
false
),
fvm
)
);
cellFldPtr = readFieldPtr_.operator->();
} }
const volScalarField& cellFld = *cellFldPtr;
// For holding the volScalarField read in.
autoPtr<volScalarField> fieldReadPtr;
if (!cellFldPtr)
{
// Bit of a hack. Read field and store.
fieldReadPtr = autoPtr<volScalarField>::New
(
IOobject
(
fieldName_,
fvm.time().timeName(),
fvm,
IOobject::MUST_READ,
IOobject::NO_WRITE,
false
),
fvm
);
}
const volScalarField& cellFld =
(fieldReadPtr.valid() ? *fieldReadPtr : *cellFldPtr);
thresholdCellFaces surf thresholdCellFaces surf
@ -123,7 +118,7 @@ bool Foam::sampledThresholdCellFaces::updateGeometry() const
).MeshedSurface<face>::transfer(surf); ).MeshedSurface<face>::transfer(surf);
meshCells_.transfer(surf.meshCells()); meshCells_.transfer(surf.meshCells());
// clear derived data // Clear derived data
sampledSurface::clearGeom(); sampledSurface::clearGeom();
if (debug) if (debug)
@ -169,12 +164,6 @@ Foam::sampledThresholdCellFaces::sampledThresholdCellFaces
} }
// * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * //
Foam::sampledThresholdCellFaces::~sampledThresholdCellFaces()
{}
// * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * // // * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
bool Foam::sampledThresholdCellFaces::needsUpdate() const bool Foam::sampledThresholdCellFaces::needsUpdate() const
@ -207,46 +196,46 @@ bool Foam::sampledThresholdCellFaces::update()
Foam::tmp<Foam::scalarField> Foam::sampledThresholdCellFaces::sample Foam::tmp<Foam::scalarField> Foam::sampledThresholdCellFaces::sample
( (
const volScalarField& vField const interpolation<scalar>& sampler
) const ) const
{ {
return sampleField(vField); return sampleOnFaces(sampler);
} }
Foam::tmp<Foam::vectorField> Foam::sampledThresholdCellFaces::sample Foam::tmp<Foam::vectorField> Foam::sampledThresholdCellFaces::sample
( (
const volVectorField& vField const interpolation<vector>& sampler
) const ) const
{ {
return sampleField(vField); return sampleOnFaces(sampler);
} }
Foam::tmp<Foam::sphericalTensorField> Foam::sampledThresholdCellFaces::sample Foam::tmp<Foam::sphericalTensorField> Foam::sampledThresholdCellFaces::sample
( (
const volSphericalTensorField& vField const interpolation<sphericalTensor>& sampler
) const ) const
{ {
return sampleField(vField); return sampleOnFaces(sampler);
} }
Foam::tmp<Foam::symmTensorField> Foam::sampledThresholdCellFaces::sample Foam::tmp<Foam::symmTensorField> Foam::sampledThresholdCellFaces::sample
( (
const volSymmTensorField& vField const interpolation<symmTensor>& sampler
) const ) const
{ {
return sampleField(vField); return sampleOnFaces(sampler);
} }
Foam::tmp<Foam::tensorField> Foam::sampledThresholdCellFaces::sample Foam::tmp<Foam::tensorField> Foam::sampledThresholdCellFaces::sample
( (
const volTensorField& vField const interpolation<tensor>& sampler
) const ) const
{ {
return sampleField(vField); return sampleOnFaces(sampler);
} }
@ -255,7 +244,7 @@ Foam::tmp<Foam::scalarField> Foam::sampledThresholdCellFaces::interpolate
const interpolation<scalar>& interpolator const interpolation<scalar>& interpolator
) const ) const
{ {
return interpolateField(interpolator); return sampleOnPoints(interpolator);
} }
@ -264,7 +253,7 @@ Foam::tmp<Foam::vectorField> Foam::sampledThresholdCellFaces::interpolate
const interpolation<vector>& interpolator const interpolation<vector>& interpolator
) const ) const
{ {
return interpolateField(interpolator); return sampleOnPoints(interpolator);
} }
Foam::tmp<Foam::sphericalTensorField> Foam::tmp<Foam::sphericalTensorField>
@ -273,7 +262,7 @@ Foam::sampledThresholdCellFaces::interpolate
const interpolation<sphericalTensor>& interpolator const interpolation<sphericalTensor>& interpolator
) const ) const
{ {
return interpolateField(interpolator); return sampleOnPoints(interpolator);
} }
@ -282,7 +271,7 @@ Foam::tmp<Foam::symmTensorField> Foam::sampledThresholdCellFaces::interpolate
const interpolation<symmTensor>& interpolator const interpolation<symmTensor>& interpolator
) const ) const
{ {
return interpolateField(interpolator); return sampleOnPoints(interpolator);
} }
@ -291,7 +280,7 @@ Foam::tmp<Foam::tensorField> Foam::sampledThresholdCellFaces::interpolate
const interpolation<tensor>& interpolator const interpolation<tensor>& interpolator
) const ) const
{ {
return interpolateField(interpolator); return sampleOnPoints(interpolator);
} }

View File

@ -3,7 +3,7 @@
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration | \\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation \\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\/ M anipulation | Copyright (C) 2016 OpenCFD Ltd. \\/ M anipulation | Copyright (C) 2016-2018 OpenCFD Ltd.
------------------------------------------------------------------------------- -------------------------------------------------------------------------------
License License
This file is part of OpenFOAM. This file is part of OpenFOAM.
@ -28,6 +28,38 @@ Description
A sampledSurface defined by the cell faces corresponding to a threshold A sampledSurface defined by the cell faces corresponding to a threshold
value. value.
This is often embedded as part of a sampled surfaces function object.
Usage
Example of function object partial specification:
\verbatim
surfaces
(
surface1
{
type thresholdCellFaces;
field rho;
lowerLimit 0.1;
}
);
\endverbatim
Where the sub-entries comprise:
\table
Property | Description | Required | Default
type | thresholdCellFaces | yes |
field | field name for threshold | yes |
lowerLimit | lower limit for threshold | partly | -Inf
upperLimit | upper limit for threshold | partly | +Inf
triangulate | triangulate faces | no | false
\endtable
Note
Must specify at least one or both of \c lowerLimit or \c upperLimit
SeeAlso
Foam::thresholdCellFaces
SourceFiles SourceFiles
sampledThresholdCellFaces.C sampledThresholdCellFaces.C
@ -88,17 +120,19 @@ class sampledThresholdCellFaces
// Do nothing (and return false) if no update was needed // Do nothing (and return false) if no update was needed
bool updateGeometry() const; bool updateGeometry() const;
//- Sample field on faces //- Sample volume field onto surface faces
template<class Type> template<class Type>
tmp<Field<Type>> sampleField tmp<Field<Type>> sampleOnFaces
( (
const GeometricField<Type, fvPatchField, volMesh>& vField const interpolation<Type>& sampler
) const; ) const;
//- Interpolate volume field onto surface points
template<class Type> template<class Type>
tmp<Field<Type>> tmp<Field<Type>> sampleOnPoints
interpolateField(const interpolation<Type>&) const; (
const interpolation<Type>& interpolator
) const;
public: public:
@ -119,7 +153,7 @@ public:
//- Destructor //- Destructor
virtual ~sampledThresholdCellFaces(); virtual ~sampledThresholdCellFaces() = default;
// Member Functions // Member Functions
@ -173,59 +207,76 @@ public:
} }
//- Sample field on surface // Sample
virtual tmp<scalarField> sample(const volScalarField&) const;
//- Sample field on surface //- Sample volume field onto surface faces
virtual tmp<vectorField> sample( const volVectorField&) const; virtual tmp<scalarField> sample
(
const interpolation<scalar>& sampler
) const;
//- Sample field on surface //- Sample volume field onto surface faces
virtual tmp<vectorField> sample
(
const interpolation<vector>& sampler
) const;
//- Sample volume field onto surface faces
virtual tmp<sphericalTensorField> sample virtual tmp<sphericalTensorField> sample
( (
const volSphericalTensorField& const interpolation<sphericalTensor>& sampler
) const; ) const;
//- Sample field on surface //- Sample volume field onto surface faces
virtual tmp<symmTensorField> sample(const volSymmTensorField&) const; virtual tmp<symmTensorField> sample
(
const interpolation<symmTensor>& sampler
) const;
//- Sample field on surface //- Sample volume field onto surface faces
virtual tmp<tensorField> sample virtual tmp<tensorField> sample
( (
const volTensorField& const interpolation<tensor>& sampler
) const; ) const;
//- Interpolate field on surface
// Interpolate
//- Interpolate volume field onto surface points
virtual tmp<scalarField> interpolate virtual tmp<scalarField> interpolate
( (
const interpolation<scalar>& const interpolation<scalar>& interpolator
) const; ) const;
//- Interpolate field on surface //- Interpolate volume field onto surface points
virtual tmp<vectorField> interpolate virtual tmp<vectorField> interpolate
( (
const interpolation<vector>& const interpolation<vector>& interpolator
) const; ) const;
//- Interpolate field on surface //- Interpolate volume field onto surface points
virtual tmp<sphericalTensorField> interpolate virtual tmp<sphericalTensorField> interpolate
( (
const interpolation<sphericalTensor>& const interpolation<sphericalTensor>& interpolator
) const; ) const;
//- Interpolate field on surface //- Interpolate volume field onto surface points
virtual tmp<symmTensorField> interpolate virtual tmp<symmTensorField> interpolate
( (
const interpolation<symmTensor>& const interpolation<symmTensor>& interpolator
) const; ) const;
//- Interpolate field on surface //- Interpolate volume field onto surface points
virtual tmp<tensorField> interpolate virtual tmp<tensorField> interpolate
( (
const interpolation<tensor>& const interpolation<tensor>& interpolator
) const; ) const;
//- Write
virtual void print(Ostream&) const; // Output
//- Print information
virtual void print(Ostream& os) const;
}; };

View File

@ -3,7 +3,7 @@
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration | \\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation \\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\/ M anipulation | \\/ M anipulation | Copyright (C) 2018 OpenCFD Ltd.
------------------------------------------------------------------------------- -------------------------------------------------------------------------------
License License
This file is part of OpenFOAM. This file is part of OpenFOAM.
@ -34,50 +34,69 @@ License
template<class Type> template<class Type>
Foam::tmp<Foam::Field<Type>> Foam::tmp<Foam::Field<Type>>
Foam::sampledThresholdCellFaces::sampleField Foam::sampledThresholdCellFaces::sampleOnFaces
( (
const GeometricField<Type, fvPatchField, volMesh>& vField const interpolation<Type>& sampler
) const ) const
{ {
// Recreate geometry if time has changed updateGeometry(); // Recreate geometry if time has changed
updateGeometry();
return tmp<Field<Type>>::New(vField, meshCells_); const labelList& elements = meshCells_;
const label len = faces().size();
auto tvalues = tmp<Field<Type>>::New(len);
auto& values = tvalues.ref();
const faceList& fcs = faces();
const pointField& pts = points();
for (label i=0; i < len; ++i)
{
const label celli = elements[i];
const point pt = fcs[i].centre(pts);
values[i] = sampler.interpolate(pt, celli);
}
return tvalues;
} }
template<class Type> template<class Type>
Foam::tmp<Foam::Field<Type>> Foam::tmp<Foam::Field<Type>>
Foam::sampledThresholdCellFaces::interpolateField Foam::sampledThresholdCellFaces::sampleOnPoints
( (
const interpolation<Type>& interpolator const interpolation<Type>& interpolator
) const ) const
{ {
// Recreate geometry if time has changed updateGeometry(); // Recreate geometry if time has changed
updateGeometry();
const labelList& elements = meshCells_;
// One value per point // One value per point
tmp<Field<Type>> tvalues(new Field<Type>(points().size())); auto tvalues = tmp<Field<Type>>::New(points().size(), Zero);
Field<Type>& values = tvalues.ref(); auto& values = tvalues.ref();
boolList pointDone(points().size(), false); bitSet pointDone(points().size());
forAll(faces(), cutFacei) const faceList& fcs = faces();
const pointField& pts = points();
forAll(fcs, i)
{ {
const face& f = faces()[cutFacei]; const face& f = fcs[i];
const label celli = elements[i];
forAll(f, faceVertI) for (const label pointi : f)
{ {
label pointi = f[faceVertI]; if (pointDone.set(pointi))
if (!pointDone[pointi])
{ {
values[pointi] = interpolator.interpolate values[pointi] = interpolator.interpolate
( (
points()[pointi], pts[pointi],
meshCells_[cutFacei] celli
); );
pointDone[pointi] = true;
} }
} }
} }

View File

@ -3,7 +3,7 @@
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration | \\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation \\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\/ M anipulation | Copyright (C) 2016 OpenCFD Ltd. \\/ M anipulation | Copyright (C) 2016-2018 OpenCFD Ltd.
------------------------------------------------------------------------------- -------------------------------------------------------------------------------
License License
This file is part of OpenFOAM. This file is part of OpenFOAM.
@ -30,7 +30,6 @@ License
#include "treeDataCell.H" #include "treeDataCell.H"
#include "treeDataFace.H" #include "treeDataFace.H"
#include "meshTools.H" #include "meshTools.H"
#include "addToRunTimeSelectionTable.H" #include "addToRunTimeSelectionTable.H"
// * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * // // * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * //
@ -138,45 +137,45 @@ bool Foam::sampledDiscreteSurface::sampleAndStore
Foam::tmp<Foam::scalarField> Foam::sampledDiscreteSurface::sample Foam::tmp<Foam::scalarField> Foam::sampledDiscreteSurface::sample
( (
const volScalarField& vField const interpolation<scalar>& sampler
) const ) const
{ {
return SurfaceSource::sampleField(vField); return SurfaceSource::sampleOnFaces(sampler);
} }
Foam::tmp<Foam::vectorField> Foam::sampledDiscreteSurface::sample Foam::tmp<Foam::vectorField> Foam::sampledDiscreteSurface::sample
( (
const volVectorField& vField const interpolation<vector>& sampler
) const ) const
{ {
return SurfaceSource::sampleField(vField); return SurfaceSource::sampleOnFaces(sampler);
} }
Foam::tmp<Foam::sphericalTensorField> Foam::sampledDiscreteSurface::sample Foam::tmp<Foam::sphericalTensorField> Foam::sampledDiscreteSurface::sample
( (
const volSphericalTensorField& vField const interpolation<sphericalTensor>& sampler
) const ) const
{ {
return SurfaceSource::sampleField(vField); return SurfaceSource::sampleOnFaces(sampler);
} }
Foam::tmp<Foam::symmTensorField> Foam::sampledDiscreteSurface::sample Foam::tmp<Foam::symmTensorField> Foam::sampledDiscreteSurface::sample
( (
const volSymmTensorField& vField const interpolation<symmTensor>& sampler
) const ) const
{ {
return SurfaceSource::sampleField(vField); return SurfaceSource::sampleOnFaces(sampler);
} }
Foam::tmp<Foam::tensorField> Foam::sampledDiscreteSurface::sample Foam::tmp<Foam::tensorField> Foam::sampledDiscreteSurface::sample
( (
const volTensorField& vField const interpolation<tensor>& sampler
) const ) const
{ {
return SurfaceSource::sampleField(vField); return SurfaceSource::sampleOnFaces(sampler);
} }
@ -185,7 +184,7 @@ Foam::tmp<Foam::scalarField> Foam::sampledDiscreteSurface::interpolate
const interpolation<scalar>& interpolator const interpolation<scalar>& interpolator
) const ) const
{ {
return SurfaceSource::interpolateField(interpolator); return SurfaceSource::sampleOnPoints(interpolator);
} }
@ -194,7 +193,7 @@ Foam::tmp<Foam::vectorField> Foam::sampledDiscreteSurface::interpolate
const interpolation<vector>& interpolator const interpolation<vector>& interpolator
) const ) const
{ {
return SurfaceSource::interpolateField(interpolator); return SurfaceSource::sampleOnPoints(interpolator);
} }
Foam::tmp<Foam::sphericalTensorField> Foam::sampledDiscreteSurface::interpolate Foam::tmp<Foam::sphericalTensorField> Foam::sampledDiscreteSurface::interpolate
@ -202,7 +201,7 @@ Foam::tmp<Foam::sphericalTensorField> Foam::sampledDiscreteSurface::interpolate
const interpolation<sphericalTensor>& interpolator const interpolation<sphericalTensor>& interpolator
) const ) const
{ {
return SurfaceSource::interpolateField(interpolator); return SurfaceSource::sampleOnPoints(interpolator);
} }
@ -211,7 +210,7 @@ Foam::tmp<Foam::symmTensorField> Foam::sampledDiscreteSurface::interpolate
const interpolation<symmTensor>& interpolator const interpolation<symmTensor>& interpolator
) const ) const
{ {
return SurfaceSource::interpolateField(interpolator); return SurfaceSource::sampleOnPoints(interpolator);
} }
@ -220,7 +219,7 @@ Foam::tmp<Foam::tensorField> Foam::sampledDiscreteSurface::interpolate
const interpolation<tensor>& interpolator const interpolation<tensor>& interpolator
) const ) const
{ {
return SurfaceSource::interpolateField(interpolator); return SurfaceSource::sampleOnPoints(interpolator);
} }

View File

@ -3,7 +3,7 @@
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration | \\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation \\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\/ M anipulation | Copyright (C) 2016 OpenCFD Ltd. \\/ M anipulation | Copyright (C) 2016-2018 OpenCFD Ltd.
------------------------------------------------------------------------------- -------------------------------------------------------------------------------
License License
This file is part of OpenFOAM. This file is part of OpenFOAM.
@ -70,17 +70,19 @@ class sampledDiscreteSurface
// Private Member Functions // Private Member Functions
//- Sample field on faces //- Sample volume field onto surface faces
template<class Type> template<class Type>
tmp<Field<Type>> sampleField tmp<Field<Type>> sampleOnFaces
( (
const GeometricField<Type, fvPatchField, volMesh>& vField const interpolation<Type>& sampler
) const; ) const;
//- Interpolate volume field onto surface points
template<class Type> template<class Type>
tmp<Field<Type>> tmp<Field<Type>> sampleOnPoints
interpolateField(const interpolation<Type>&) const; (
const interpolation<Type>& interpolator
) const;
public: public:
@ -199,70 +201,76 @@ public:
) const; ) const;
//- Sample field on surface // Sample
//- Sample volume field onto surface faces
virtual tmp<scalarField> sample virtual tmp<scalarField> sample
( (
const volScalarField& const interpolation<scalar>& sampler
) const; ) const;
//- Sample field on surface //- Sample volume field onto surface faces
virtual tmp<vectorField> sample virtual tmp<vectorField> sample
( (
const volVectorField& const interpolation<vector>& sampler
) const; ) const;
//- Sample field on surface //- Sample volume field onto surface faces
virtual tmp<sphericalTensorField> sample virtual tmp<sphericalTensorField> sample
( (
const volSphericalTensorField& const interpolation<sphericalTensor>& sampler
) const; ) const;
//- Sample field on surface //- Sample volume field onto surface faces
virtual tmp<symmTensorField> sample virtual tmp<symmTensorField> sample
( (
const volSymmTensorField& const interpolation<symmTensor>& sampler
) const; ) const;
//- Sample field on surface //- Sample volume field onto surface faces
virtual tmp<tensorField> sample virtual tmp<tensorField> sample
( (
const volTensorField& const interpolation<tensor>& sampler
) const; ) const;
//- Interpolate field on surface // Interpolate
//- Interpolate volume field onto surface points
virtual tmp<scalarField> interpolate virtual tmp<scalarField> interpolate
( (
const interpolation<scalar>& const interpolation<scalar>& interpolator
) const; ) const;
//- Interpolate volume field onto surface points
//- Interpolate field on surface
virtual tmp<vectorField> interpolate virtual tmp<vectorField> interpolate
( (
const interpolation<vector>& const interpolation<vector>& interpolator
) const; ) const;
//- Interpolate field on surface //- Interpolate volume field onto surface points
virtual tmp<sphericalTensorField> interpolate virtual tmp<sphericalTensorField> interpolate
( (
const interpolation<sphericalTensor>& const interpolation<sphericalTensor>& interpolator
) const; ) const;
//- Interpolate field on surface //- Interpolate volume field onto surface points
virtual tmp<symmTensorField> interpolate virtual tmp<symmTensorField> interpolate
( (
const interpolation<symmTensor>& const interpolation<symmTensor>& interpolator
) const; ) const;
//- Interpolate field on surface //- Interpolate volume field onto surface points
virtual tmp<tensorField> interpolate virtual tmp<tensorField> interpolate
( (
const interpolation<tensor>& const interpolation<tensor>& interpolator
) const; ) const;
//- Write information
virtual void print(Ostream&) const; // Output
//- Write
virtual void print(Ostream& os) const;
}; };

View File

@ -28,5 +28,4 @@ License
// * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * // // * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * //
// ************************************************************************* // // ************************************************************************* //

View File

@ -130,7 +130,7 @@ Foam::fileName Foam::ensightSurfaceWriter::write
} }
// create write methods // Create all write methods
defineSurfaceWriterWriteFields(Foam::ensightSurfaceWriter); defineSurfaceWriterWriteFields(Foam::ensightSurfaceWriter);

View File

@ -27,6 +27,24 @@ Class
Description Description
A surfaceWriter for Ensight format. A surfaceWriter for Ensight format.
\verbatim
formatOptions
{
ensight
{
format ascii;
collateTimes true;
}
}
\endverbatim
Format options:
\table
Property | Description | Required | Default
format | ascii/binary | no | ascii
collateTimes | use common geometry for times | no | true
\endtable
SourceFiles SourceFiles
ensightSurfaceWriter.C ensightSurfaceWriter.C
@ -43,7 +61,7 @@ namespace Foam
{ {
/*---------------------------------------------------------------------------*\ /*---------------------------------------------------------------------------*\
Class ensightSurfaceWriter Declaration Class ensightSurfaceWriter Declaration
\*---------------------------------------------------------------------------*/ \*---------------------------------------------------------------------------*/
class ensightSurfaceWriter class ensightSurfaceWriter
@ -55,7 +73,7 @@ class ensightSurfaceWriter
//- Write option (default: IOstream::ASCII) //- Write option (default: IOstream::ASCII)
IOstream::streamFormat writeFormat_; IOstream::streamFormat writeFormat_;
//- Collate times (default: ASCII) //- Collate times (default: true)
bool collateTimes_; bool collateTimes_;

View File

@ -306,11 +306,11 @@ Foam::fileName Foam::ensightSurfaceWriter::writeCollated
<< "time values:" << nl; << "time values:" << nl;
label count = 0; label count = 0;
forAll(times, timeI) forAll(times, timei)
{ {
osCase << ' ' << setw(12) << times[timeI]; osCase << ' ' << setw(12) << times[timei];
if (++count % 6 == 0) if (!(++count % 6))
{ {
osCase << nl; osCase << nl;
} }
@ -335,7 +335,7 @@ Foam::fileName Foam::ensightSurfaceWriter::writeCollated
{ {
Info<< "Writing mesh file to " << meshFile.name() << endl; Info<< "Writing mesh file to " << meshFile.name() << endl;
} }
// use two-argument form for path-name to avoid validating the base-dir // Use two-argument form for path-name to avoid validating the base-dir
ensightGeoFile osGeom(meshFile.path(), meshFile.name(), writeFormat_); ensightGeoFile osGeom(meshFile.path(), meshFile.name(), writeFormat_);
osGeom << ensPart; osGeom << ensPart;
} }
@ -352,7 +352,7 @@ Foam::fileName Foam::ensightSurfaceWriter::writeCollated
fileName dataDir = baseDir/"data"/timeString; fileName dataDir = baseDir/"data"/timeString;
// as per mkdir -p "data/000000" // As per mkdir -p "data/000000"
mkDir(dataDir); mkDir(dataDir);
// Write field // Write field
@ -378,7 +378,7 @@ Foam::fileName Foam::ensightSurfaceWriter::writeCollated
isNodeValues isNodeValues
); );
// place a timestamp in the directory for future reference // Place a timestamp in the directory for future reference
{ {
OFstream timeStamp(dataDir/"time"); OFstream timeStamp(dataDir/"time");
timeStamp timeStamp

View File

@ -43,7 +43,7 @@ Description
// Optional format // Optional format
format free; // short, long, free format free; // short, long, free
} }
}; }
\endverbatim \endverbatim
SourceFiles SourceFiles

View File

@ -0,0 +1,137 @@
/*---------------------------------------------------------------------------*\
========= |
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration |
\\ / A nd | Copyright (C) 2018 OpenCFD Ltd.
\\/ M anipulation |
-------------------------------------------------------------------------------
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 <http://www.gnu.org/licenses/>.
\*---------------------------------------------------------------------------*/
#include "surfMeshSampleDistanceSurface.H"
#include "dictionary.H"
#include "polyMesh.H"
#include "volFields.H"
#include "coordinateSystem.H"
#include "addToRunTimeSelectionTable.H"
// * * * * * * * * * * * * * * Static Data Members * * * * * * * * * * * * * //
namespace Foam
{
defineTypeNameAndDebug(surfMeshSampleDistanceSurface, 0);
addNamedToRunTimeSelectionTable
(
surfMeshSample,
surfMeshSampleDistanceSurface,
word,
distanceSurface
);
}
// * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * //
Foam::surfMeshSampleDistanceSurface::surfMeshSampleDistanceSurface
(
const word& name,
const polyMesh& mesh,
const dictionary& dict
)
:
surfMeshSample(name, mesh, dict),
SurfaceSource(name, mesh, dict),
needsUpdate_(true)
{}
// * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
bool Foam::surfMeshSampleDistanceSurface::needsUpdate() const
{
return needsUpdate_;
}
bool Foam::surfMeshSampleDistanceSurface::expire()
{
// Already marked as expired
if (needsUpdate_)
{
return false;
}
needsUpdate_ = true;
return true;
}
bool Foam::surfMeshSampleDistanceSurface::update()
{
if (!needsUpdate_)
{
return false;
}
SurfaceSource::createGeometry();
// Transfer content
getOrCreateSurfMesh().transfer
(
SurfaceSource::surface()
);
if (debug)
{
print(Pout);
Pout<< endl;
}
needsUpdate_ = false;
return true;
}
bool Foam::surfMeshSampleDistanceSurface::sample
(
const word& fieldName,
const word& sampleScheme
) const
{
return
(
sampleType<scalar>(fieldName, sampleScheme)
|| sampleType<vector>(fieldName, sampleScheme)
|| sampleType<sphericalTensor>(fieldName, sampleScheme)
|| sampleType<symmTensor>(fieldName, sampleScheme)
|| sampleType<tensor>(fieldName, sampleScheme)
);
}
void Foam::surfMeshSampleDistanceSurface::print(Ostream& os) const
{
os << "distanceSurface: " << name() << " :"
<< " surface:" << surfaceName()
<< " distance:" << distance()
<< " faces:" << surface().faces().size()
<< " points:" << surface().points().size();
}
// ************************************************************************* //

View File

@ -0,0 +1,154 @@
/*---------------------------------------------------------------------------*\
========= |
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration |
\\ / A nd | Copyright (C) 2018 OpenCFD Ltd.
\\/ M anipulation |
-------------------------------------------------------------------------------
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 <http://www.gnu.org/licenses/>.
Class
Foam::surfMeshSampleDistanceSurface
Description
Sampling surfFields onto a surfMesh based on a plane.
The cuttingPlane algorithm 'cuts' the mesh.
The plane is triangulated by default.
Note
Does not actually cut until update() called.
SourceFiles
surfMeshSampleDistanceSurface.C
surfMeshSampleDistanceSurfaceTemplates.C
\*---------------------------------------------------------------------------*/
#ifndef surfMeshSampleDistanceSurface_H
#define surfMeshSampleDistanceSurface_H
#include "surfMeshSample.H"
#include "distanceSurface.H"
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
namespace Foam
{
/*---------------------------------------------------------------------------*\
Class surfMeshSampleDistanceSurface Declaration
\*---------------------------------------------------------------------------*/
class surfMeshSampleDistanceSurface
:
public surfMeshSample,
private distanceSurface
{
// Private typedefs for convenience
typedef distanceSurface SurfaceSource;
// Private data
//- Track if the surface needs an update
mutable bool needsUpdate_;
// Private Member Functions
//- Sample field on surface
template<class Type>
tmp<Field<Type>> sampleOnFaces
(
const interpolation<Type>& sampler
) const;
//- Sample field on surface.
template<class Type>
bool sampleType
(
const word& fieldName,
const word& sampleScheme
) const;
public:
//- Runtime type information
TypeName("surfMeshSampleDistanceSurface");
// Constructors
//- Construct from dictionary
surfMeshSampleDistanceSurface
(
const word& name,
const polyMesh& mesh,
const dictionary& dict
);
//- Destructor
virtual ~surfMeshSampleDistanceSurface() = default;
// Member Functions
//- The surface is from surfMesh
using surfMeshSample::surface;
//- Does the surface need an update?
virtual bool needsUpdate() const;
//- Mark the surface as needing an update.
// May also free up unneeded data.
// Return false if surface was already marked as expired.
virtual bool expire();
//- Update the surface as required.
// Do nothing (and return false) if no update was needed
virtual bool update();
//- Sample the volume field onto surface
virtual bool sample
(
const word& fieldName,
const word& sampleScheme = "cell"
) const;
//- Write
virtual void print(Ostream& os) const;
};
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
} // End namespace Foam
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
#ifdef NoRepository
#include "surfMeshSampleDistanceSurfaceTemplates.C"
#endif
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
#endif
// ************************************************************************* //

View File

@ -0,0 +1,72 @@
/*---------------------------------------------------------------------------*\
========= |
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration |
\\ / A nd | Copyright (C) 2018 OpenCFD Ltd.
\\/ M anipulation |
-------------------------------------------------------------------------------
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 <http://www.gnu.org/licenses/>.
\*---------------------------------------------------------------------------*/
#include "surfMeshSampleDistanceSurface.H"
// * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * //
template<class Type>
Foam::tmp<Foam::Field<Type>>
Foam::surfMeshSampleDistanceSurface::sampleOnFaces
(
const interpolation<Type>& sampler
) const
{
return surfMeshSample::sampleOnFaces
(
sampler,
SurfaceSource::meshCells(),
surface().faces(),
surface().points()
);
}
template<class Type>
bool Foam::surfMeshSampleDistanceSurface::sampleType
(
const word& fieldName,
const word& sampleScheme
) const
{
typedef GeometricField<Type, fvPatchField, volMesh> VolFieldType;
const auto* volFldPtr = mesh().lookupObjectPtr<VolFieldType>(fieldName);
if (!volFldPtr)
{
return false;
}
auto samplerPtr = interpolation<Type>::New(sampleScheme, *volFldPtr);
getOrCreateSurfField<Type>(*volFldPtr).field() =
sampleOnFaces(*samplerPtr);
return true;
}
// ************************************************************************* //

View File

@ -2,7 +2,7 @@
========= | ========= |
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration | \\ / O peration |
\\ / A nd | Copyright (C) 2016 OpenCFD Ltd. \\ / A nd | Copyright (C) 2016-2018 OpenCFD Ltd.
\\/ M anipulation | \\/ M anipulation |
------------------------------------------------------------------------------- -------------------------------------------------------------------------------
License License
@ -23,7 +23,7 @@ License
\*---------------------------------------------------------------------------*/ \*---------------------------------------------------------------------------*/
#include "surfMeshPlaneSampler.H" #include "surfMeshSamplePlane.H"
#include "dictionary.H" #include "dictionary.H"
#include "polyMesh.H" #include "polyMesh.H"
#include "volFields.H" #include "volFields.H"
@ -34,31 +34,20 @@ License
namespace Foam namespace Foam
{ {
defineTypeNameAndDebug(surfMeshPlaneSampler, 0); defineTypeNameAndDebug(surfMeshSamplePlane, 0);
addNamedToRunTimeSelectionTable addNamedToRunTimeSelectionTable
( (
surfMeshSampler, surfMeshSample,
surfMeshPlaneSampler, surfMeshSamplePlane,
word, word,
plane plane
); );
} }
// * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * //
void Foam::surfMeshPlaneSampler::transferContent()
{
SurfaceSource& src = static_cast<SurfaceSource&>(*this);
surfMesh& dst = getOrCreateSurfMesh();
dst.transfer(src);
}
// * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * // // * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * //
Foam::surfMeshPlaneSampler::surfMeshPlaneSampler Foam::surfMeshSamplePlane::surfMeshSamplePlane
( (
const word& name, const word& name,
const polyMesh& mesh, const polyMesh& mesh,
@ -67,7 +56,7 @@ Foam::surfMeshPlaneSampler::surfMeshPlaneSampler
const bool triangulate const bool triangulate
) )
: :
surfMeshSampler(name, mesh), surfMeshSample(name, mesh),
SurfaceSource(planeDesc), SurfaceSource(planeDesc),
zoneKey_(zoneKey), zoneKey_(zoneKey),
bounds_(), bounds_(),
@ -82,14 +71,14 @@ Foam::surfMeshPlaneSampler::surfMeshPlaneSampler
} }
Foam::surfMeshPlaneSampler::surfMeshPlaneSampler Foam::surfMeshSamplePlane::surfMeshSamplePlane
( (
const word& name, const word& name,
const polyMesh& mesh, const polyMesh& mesh,
const dictionary& dict const dictionary& dict
) )
: :
surfMeshSampler(name, mesh, dict), surfMeshSample(name, mesh, dict),
SurfaceSource(plane(dict)), SurfaceSource(plane(dict)),
zoneKey_(dict.lookupOrDefault<keyType>("zone", keyType::null)), zoneKey_(dict.lookupOrDefault<keyType>("zone", keyType::null)),
bounds_(dict.lookupOrDefault("bounds", boundBox::invertedBox)), bounds_(dict.lookupOrDefault("bounds", boundBox::invertedBox)),
@ -119,13 +108,13 @@ Foam::surfMeshPlaneSampler::surfMeshPlaneSampler
// * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * // // * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
bool Foam::surfMeshPlaneSampler::needsUpdate() const bool Foam::surfMeshSamplePlane::needsUpdate() const
{ {
return needsUpdate_; return needsUpdate_;
} }
bool Foam::surfMeshPlaneSampler::expire() bool Foam::surfMeshSamplePlane::expire()
{ {
// Already marked as expired // Already marked as expired
if (needsUpdate_) if (needsUpdate_)
@ -138,7 +127,7 @@ bool Foam::surfMeshPlaneSampler::expire()
} }
bool Foam::surfMeshPlaneSampler::update() bool Foam::surfMeshSamplePlane::update()
{ {
if (!needsUpdate_) if (!needsUpdate_)
{ {
@ -243,32 +232,37 @@ bool Foam::surfMeshPlaneSampler::update()
Pout<< endl; Pout<< endl;
} }
transferContent(); // Transfer content
getOrCreateSurfMesh().transfer
(
static_cast<SurfaceSource&>(*this)
);
needsUpdate_ = false; needsUpdate_ = false;
return true; return true;
} }
bool Foam::surfMeshPlaneSampler::sample bool Foam::surfMeshSamplePlane::sample
( (
const word& fieldName const word& fieldName,
const word& sampleScheme
) const ) const
{ {
return return
( (
sampleType<scalar>(fieldName) sampleType<scalar>(fieldName, sampleScheme)
|| sampleType<vector>(fieldName) || sampleType<vector>(fieldName, sampleScheme)
|| sampleType<sphericalTensor>(fieldName) || sampleType<sphericalTensor>(fieldName, sampleScheme)
|| sampleType<symmTensor>(fieldName) || sampleType<symmTensor>(fieldName, sampleScheme)
|| sampleType<tensor>(fieldName) || sampleType<tensor>(fieldName, sampleScheme)
); );
} }
void Foam::surfMeshPlaneSampler::print(Ostream& os) const void Foam::surfMeshSamplePlane::print(Ostream& os) const
{ {
os << "surfMeshPlaneSampler: " << name() << " :" os << "surfMeshSamplePlane: " << name() << " :"
<< " base:" << cuttingPlane::refPoint() << " base:" << cuttingPlane::refPoint()
<< " normal:" << cuttingPlane::normal() << " normal:" << cuttingPlane::normal()
<< " triangulate:" << triangulate_ << " triangulate:" << triangulate_

View File

@ -2,7 +2,7 @@
========= | ========= |
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration | \\ / O peration |
\\ / A nd | Copyright (C) 2016 OpenCFD Ltd. \\ / A nd | Copyright (C) 2016-2018 OpenCFD Ltd.
\\/ M anipulation | \\/ M anipulation |
------------------------------------------------------------------------------- -------------------------------------------------------------------------------
License License
@ -22,7 +22,7 @@ License
along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>. along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>.
Class Class
Foam::surfMeshPlaneSampler Foam::surfMeshSamplePlane
Description Description
Sampling surfFields onto a surfMesh based on a plane. Sampling surfFields onto a surfMesh based on a plane.
@ -33,15 +33,15 @@ Note
Does not actually cut until update() called. Does not actually cut until update() called.
SourceFiles SourceFiles
surfMeshPlaneSampler.C surfMeshSamplePlane.C
surfMeshPlaneSamplerTemplates.C surfMeshSamplePlaneTemplates.C
\*---------------------------------------------------------------------------*/ \*---------------------------------------------------------------------------*/
#ifndef surfMeshPlaneSampler_H #ifndef surfMeshSamplePlane_H
#define surfMeshPlaneSampler_H #define surfMeshSamplePlane_H
#include "surfMeshSampler.H" #include "surfMeshSample.H"
#include "cuttingPlane.H" #include "cuttingPlane.H"
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
@ -50,12 +50,12 @@ namespace Foam
{ {
/*---------------------------------------------------------------------------*\ /*---------------------------------------------------------------------------*\
Class surfMeshPlaneSampler Declaration Class surfMeshSamplePlane Declaration
\*---------------------------------------------------------------------------*/ \*---------------------------------------------------------------------------*/
class surfMeshPlaneSampler class surfMeshSamplePlane
: :
public surfMeshSampler, public surfMeshSample,
private cuttingPlane private cuttingPlane
{ {
// Private typedefs for convenience // Private typedefs for convenience
@ -78,36 +78,33 @@ class surfMeshPlaneSampler
// Private Member Functions // Private Member Functions
//- Transfer mesh content from SurfaceSource to surfMesh //- Sample field on surface
void transferContent(); template<class Type>
tmp<Field<Type>> sampleOnFaces
(
const interpolation<Type>& sampler
) const;
//- Sample field on surface. //- Sample field on surface.
template<class Type> template<class Type>
bool sampleType bool sampleType
( (
const word& fieldName const word& fieldName,
) const; const word& sampleScheme
//- Sample field on surface
template<class Type>
tmp<Field<Type>> sampleField
(
const GeometricField<Type, fvPatchField, volMesh>& vField
) const; ) const;
public: public:
//- Runtime type information //- Runtime type information
TypeName("surfMeshPlaneSampler"); TypeName("surfMeshSamplePlane");
// Constructors // Constructors
//- Construct from components //- Construct from components
surfMeshPlaneSampler surfMeshSamplePlane
( (
const word& name, const word& name,
const polyMesh& mesh, const polyMesh& mesh,
@ -117,7 +114,7 @@ public:
); );
//- Construct from dictionary //- Construct from dictionary
surfMeshPlaneSampler surfMeshSamplePlane
( (
const word& name, const word& name,
const polyMesh& mesh, const polyMesh& mesh,
@ -126,7 +123,7 @@ public:
//- Destructor //- Destructor
virtual ~surfMeshPlaneSampler() = default; virtual ~surfMeshSamplePlane() = default;
// Member Functions // Member Functions
@ -144,11 +141,15 @@ public:
virtual bool update(); virtual bool update();
//- Sample the volume field onto surface //- Sample the volume field onto surface
virtual bool sample(const word& fieldName) const; virtual bool sample
(
const word& fieldName,
const word& sampleScheme = "cell"
) const;
//- Write //- Write
virtual void print(Ostream&) const; virtual void print(Ostream& os) const;
}; };
@ -159,7 +160,7 @@ public:
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
#ifdef NoRepository #ifdef NoRepository
#include "surfMeshPlaneSamplerTemplates.C" #include "surfMeshSamplePlaneTemplates.C"
#endif #endif
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //

View File

@ -2,7 +2,7 @@
========= | ========= |
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration | \\ / O peration |
\\ / A nd | Copyright (C) 2016 OpenCFD Ltd. \\ / A nd | Copyright (C) 2016-2018 OpenCFD Ltd.
\\/ M anipulation | \\/ M anipulation |
------------------------------------------------------------------------------- -------------------------------------------------------------------------------
License License
@ -23,41 +23,50 @@ License
\*---------------------------------------------------------------------------*/ \*---------------------------------------------------------------------------*/
#include "surfMeshPlaneSampler.H" #include "surfMeshSamplePlane.H"
// * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * // // * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * //
template<class Type> template<class Type>
bool Foam::surfMeshPlaneSampler::sampleType Foam::tmp<Foam::Field<Type>>
Foam::surfMeshSamplePlane::sampleOnFaces
( (
const word& fieldName const interpolation<Type>& sampler
) const
{
return surfMeshSample::sampleOnFaces
(
sampler,
SurfaceSource::meshCells(),
surface().faces(),
surface().points()
);
}
template<class Type>
bool Foam::surfMeshSamplePlane::sampleType
(
const word& fieldName,
const word& sampleScheme
) const ) const
{ {
typedef GeometricField<Type, fvPatchField, volMesh> VolFieldType; typedef GeometricField<Type, fvPatchField, volMesh> VolFieldType;
if (!mesh().foundObject<VolFieldType>(fieldName)) const auto* volFldPtr = mesh().lookupObjectPtr<VolFieldType>(fieldName);
if (!volFldPtr)
{ {
return false; return false;
} }
const VolFieldType& fld = mesh().lookupObject<VolFieldType>(fieldName); auto samplerPtr = interpolation<Type>::New(sampleScheme, *volFldPtr);
getOrCreateSurfField<Type>(fld).field() getOrCreateSurfField<Type>(*volFldPtr).field() =
= SurfaceSource::sample<Type>(fld); sampleOnFaces(*samplerPtr);
return true; return true;
} }
template<class Type>
Foam::tmp<Foam::Field<Type>>
Foam::surfMeshPlaneSampler::sampleField
(
const GeometricField<Type, fvPatchField, volMesh>& vField
) const
{
return SurfaceSource::sample<Type>(vField);
}
// ************************************************************************* // // ************************************************************************* //

View File

@ -23,7 +23,7 @@ License
\*---------------------------------------------------------------------------*/ \*---------------------------------------------------------------------------*/
#include "surfMeshSampler.H" #include "surfMeshSample.H"
#include "MeshedSurfaces.H" #include "MeshedSurfaces.H"
#include "addToRunTimeSelectionTable.H" #include "addToRunTimeSelectionTable.H"
@ -31,15 +31,15 @@ License
namespace Foam namespace Foam
{ {
defineTypeNameAndDebug(surfMeshSampler, 0); defineTypeNameAndDebug(surfMeshSample, 0);
defineRunTimeSelectionTable(surfMeshSampler, word); defineRunTimeSelectionTable(surfMeshSample, word);
} }
// * * * * * * * * * * * * Protected Member Functions * * * * * * * * * * * // // * * * * * * * * * * * * Protected Member Functions * * * * * * * * * * * //
Foam::surfMesh& Foam::surfMesh&
Foam::surfMeshSampler::getOrCreateSurfMesh() const Foam::surfMeshSample::getOrCreateSurfMesh() const
{ {
if (!mesh().foundObject<surfMesh>(name())) if (!mesh().foundObject<surfMesh>(name()))
{ {
@ -67,8 +67,8 @@ Foam::surfMeshSampler::getOrCreateSurfMesh() const
// * * * * * * * * * * * * * * * * Selectors * * * * * * * * * * * * * * * // // * * * * * * * * * * * * * * * * Selectors * * * * * * * * * * * * * * * //
Foam::autoPtr<Foam::surfMeshSampler> Foam::autoPtr<Foam::surfMeshSample>
Foam::surfMeshSampler::New Foam::surfMeshSample::New
( (
const word& name, const word& name,
const polyMesh& mesh, const polyMesh& mesh,
@ -89,13 +89,13 @@ Foam::surfMeshSampler::New
<< exit(FatalError); << exit(FatalError);
} }
return autoPtr<surfMeshSampler>(cstrIter()(name, mesh, dict)); return autoPtr<surfMeshSample>(cstrIter()(name, mesh, dict));
} }
// * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * // // * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * //
Foam::surfMeshSampler::surfMeshSampler Foam::surfMeshSample::surfMeshSample
( (
const word& name, const word& name,
const polyMesh& mesh const polyMesh& mesh
@ -106,7 +106,7 @@ Foam::surfMeshSampler::surfMeshSampler
{} {}
Foam::surfMeshSampler::surfMeshSampler Foam::surfMeshSample::surfMeshSample
( (
const word& name, const word& name,
const polyMesh& mesh, const polyMesh& mesh,
@ -122,20 +122,21 @@ Foam::surfMeshSampler::surfMeshSampler
// * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * // // * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
void Foam::surfMeshSampler::create() const void Foam::surfMeshSample::create() const
{ {
getOrCreateSurfMesh(); getOrCreateSurfMesh();
} }
const Foam::surfMesh& Foam::surfMeshSampler::surface() const const Foam::surfMesh& Foam::surfMeshSample::surface() const
{ {
return mesh().lookupObject<surfMesh>(name()); return mesh().lookupObject<surfMesh>(name());
} }
// Demonstration of using separate tmp registry // Demonstration of using separate tmp registry
// Foam::label Foam::surfMeshSampler::sample //
// Foam::label Foam::surfMeshSample::sample
// ( // (
// const objectRegistry& store, // const objectRegistry& store,
// const UList<word>& fields // const UList<word>& fields
@ -168,15 +169,16 @@ const Foam::surfMesh& Foam::surfMeshSampler::surface() const
// } // }
Foam::label Foam::surfMeshSampler::sample Foam::label Foam::surfMeshSample::sample
( (
const UList<word>& fieldNames const UList<word>& fieldNames,
const word& sampleScheme
) const ) const
{ {
label count = 0; label count = 0;
for (const word& fieldName : fieldNames) for (const word& fieldName : fieldNames)
{ {
if (sample(fieldName)) if (sample(fieldName, sampleScheme))
{ {
++count; ++count;
} }
@ -186,7 +188,7 @@ Foam::label Foam::surfMeshSampler::sample
} }
Foam::label Foam::surfMeshSampler::write(const wordRes& select) const Foam::label Foam::surfMeshSample::write(const wordRes& select) const
{ {
label count = label count =
( (
@ -207,7 +209,7 @@ Foam::label Foam::surfMeshSampler::write(const wordRes& select) const
void Foam::surfMeshSampler::print(Ostream& os) const void Foam::surfMeshSample::print(Ostream& os) const
{ {
os << type(); os << type();
} }

View File

@ -22,7 +22,7 @@ License
along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>. along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>.
Class Class
Foam::surfMeshSampler Foam::surfMeshSample
Group Group
grpUtilitiesFunctionObjects grpUtilitiesFunctionObjects
@ -31,13 +31,13 @@ Description
An abstract class for surfMesh with sampling. An abstract class for surfMesh with sampling.
SourceFiles SourceFiles
surfMeshSampler.C surfMeshSample.C
surfMeshSamplerTemplates.C surfMeshSampleTemplates.C
\*---------------------------------------------------------------------------*/ \*---------------------------------------------------------------------------*/
#ifndef surfMeshSampler_H #ifndef surfMeshSample_H
#define surfMeshSampler_H #define surfMeshSample_H
#include "surfMesh.H" #include "surfMesh.H"
#include "surfFields.H" #include "surfFields.H"
@ -61,13 +61,13 @@ SourceFiles
namespace Foam namespace Foam
{ {
class surfMeshSampler; class surfMeshSample;
/*---------------------------------------------------------------------------*\ /*---------------------------------------------------------------------------*\
Class surfMeshSampler Declaration Class surfMeshSample Declaration
\*---------------------------------------------------------------------------*/ \*---------------------------------------------------------------------------*/
class surfMeshSampler class surfMeshSample
{ {
// Private data // Private data
@ -78,15 +78,21 @@ class surfMeshSampler
const polyMesh& mesh_; const polyMesh& mesh_;
// Private Member Functions
// Service methods
protected: protected:
// Protected Member Functions // Protected Member Functions
//- General loop for sampling elements to faces
template<class Type>
static tmp<Field<Type>> sampleOnFaces
(
const interpolation<Type>& sampler,
const labelUList& elements,
const faceList& fcs,
const pointField& pts
);
//- Get existing or create new surfMesh //- Get existing or create new surfMesh
surfMesh& getOrCreateSurfMesh() const; surfMesh& getOrCreateSurfMesh() const;
@ -116,14 +122,14 @@ protected:
public: public:
//- Runtime type information //- Runtime type information
TypeName("surfMeshSampler"); TypeName("surfMeshSample");
//- Declare run-time constructor selection table //- Declare run-time constructor selection table
declareRunTimeSelectionTable declareRunTimeSelectionTable
( (
autoPtr, autoPtr,
surfMeshSampler, surfMeshSample,
word, word,
( (
const word& name, const word& name,
@ -149,12 +155,12 @@ public:
mesh_(mesh) mesh_(mesh)
{} {}
autoPtr<surfMeshSampler> operator()(Istream& is) const autoPtr<surfMeshSample> operator()(Istream& is) const
{ {
word name(is); word name(is);
dictionary dict(is); dictionary dict(is);
return surfMeshSampler::New(name, mesh_, dict); return surfMeshSample::New(name, mesh_, dict);
} }
}; };
@ -162,14 +168,14 @@ public:
// Constructors // Constructors
//- Construct from name, mesh //- Construct from name, mesh
surfMeshSampler surfMeshSample
( (
const word& name, const word& name,
const polyMesh& mesh const polyMesh& mesh
); );
//- Construct from dictionary //- Construct from dictionary
surfMeshSampler surfMeshSample
( (
const word& name, const word& name,
const polyMesh& mesh, const polyMesh& mesh,
@ -178,7 +184,7 @@ public:
//- Clone //- Clone
autoPtr<surfMeshSampler> clone() const autoPtr<surfMeshSample> clone() const
{ {
NotImplemented; NotImplemented;
return nullptr; return nullptr;
@ -189,7 +195,7 @@ public:
// Selectors // Selectors
//- Return a reference to the selected surface //- Return a reference to the selected surface
static autoPtr<surfMeshSampler> New static autoPtr<surfMeshSample> New
( (
const word& name, const word& name,
const polyMesh& mesh, const polyMesh& mesh,
@ -198,12 +204,12 @@ public:
//- Destructor //- Destructor
virtual ~surfMeshSampler() = default; virtual ~surfMeshSample() = default;
// Member Functions // Member Functions
// Access // Access
//- Access to the underlying mesh //- Access to the underlying mesh
const polyMesh& mesh() const const polyMesh& mesh() const
@ -238,7 +244,7 @@ public:
virtual bool update() = 0; virtual bool update() = 0;
// Edit // Edit
//- Rename //- Rename
virtual void rename(const word& newName) virtual void rename(const word& newName)
@ -247,16 +253,24 @@ public:
} }
// Execute // Execute
//- Sample from specified volume field to surface //- Sample from specified volume field to obtain surface field.
virtual bool sample(const word& fieldName) const = 0; virtual bool sample
(
const word& fieldName,
const word& sampleScheme = "cell"
) const = 0;
//- Sample from volume fields to specified surface fields. //- Sample from specified volume fields to obtain surface fields.
virtual label sample(const UList<word>& fieldNames) const; virtual label sample
(
const UList<word>& fieldNames,
const word& sampleScheme = "cell"
) const;
// Write // Write
//- Write specified fields //- Write specified fields
virtual label write(const wordRes& fieldSelection) const; virtual label write(const wordRes& fieldSelection) const;
@ -274,7 +288,7 @@ public:
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
#ifdef NoRepository #ifdef NoRepository
# include "surfMeshSamplerTemplates.C" # include "surfMeshSampleTemplates.C"
#endif #endif
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //

View File

@ -23,14 +23,50 @@ License
\*---------------------------------------------------------------------------*/ \*---------------------------------------------------------------------------*/
#include "surfMeshSampler.H" #include "surfMeshSample.H"
#include "dimensionedType.H" #include "dimensionedType.H"
// * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * // // * * * * * * * * * * * * Protected Member Functions * * * * * * * * * * * //
template<class Type>
Foam::tmp<Foam::Field<Type>>
Foam::surfMeshSample::sampleOnFaces
(
const interpolation<Type>& sampler,
const labelUList& elements,
const faceList& fcs,
const pointField& pts
)
{
const label len = elements.size();
if (len != fcs.size())
{
FatalErrorInFunction
<< "size mismatch: "
<< "sampled elements (" << len
<< ") != faces (" << fcs.size() << ')'
<< exit(FatalError);
}
auto tvalues = tmp<Field<Type>>::New(len);
auto& values = tvalues.ref();
for (label i=0; i < len; ++i)
{
const label celli = elements[i];
const point pt = fcs[i].centre(pts);
values[i] = sampler.interpolate(pt, celli);
}
return tvalues;
}
template<class Type> template<class Type>
Foam::DimensionedField<Type, Foam::surfGeoMesh>& Foam::DimensionedField<Type, Foam::surfGeoMesh>&
Foam::surfMeshSampler::getOrCreateSurfField Foam::surfMeshSample::getOrCreateSurfField
( (
const GeometricField<Type, fvPatchField, volMesh>& vField const GeometricField<Type, fvPatchField, volMesh>& vField
) const ) const
@ -68,7 +104,7 @@ Foam::surfMeshSampler::getOrCreateSurfField
// // Older code for transferring an IOField to a surfField between // // Older code for transferring an IOField to a surfField between
// // different registries // // different registries
// template<class Type> // template<class Type>
// bool Foam::surfMeshSampler::transferField // bool Foam::surfMeshSample::transferField
// ( // (
// const objectRegistry& store, // const objectRegistry& store,
// const word& fieldName // const word& fieldName
@ -104,7 +140,7 @@ Foam::surfMeshSampler::getOrCreateSurfField
template<class Type> template<class Type>
Foam::label Foam::surfMeshSampler::writeFields Foam::label Foam::surfMeshSample::writeFields
( (
const wordRes& select const wordRes& select
) const ) const
@ -112,7 +148,8 @@ Foam::label Foam::surfMeshSampler::writeFields
typedef DimensionedField<Type, surfGeoMesh> SurfFieldType; typedef DimensionedField<Type, surfGeoMesh> SurfFieldType;
const surfMesh& s = surface(); const surfMesh& s = surface();
const wordList fieldNames = s.sortedNames<SurfFieldType>(select); const wordList fieldNames(s.sortedNames<SurfFieldType>(select));
for (const word& fieldName : fieldNames) for (const word& fieldName : fieldNames)
{ {
s.lookupObject<SurfFieldType>(fieldName).write(); s.lookupObject<SurfFieldType>(fieldName).write();

View File

@ -44,7 +44,7 @@ namespace Foam
surfMeshSamplers, surfMeshSamplers,
dictionary dictionary
); );
} } // End namespace Foam
bool Foam::surfMeshSamplers::verbose_ = false; bool Foam::surfMeshSamplers::verbose_ = false;
@ -106,9 +106,11 @@ Foam::surfMeshSamplers::surfMeshSamplers
) )
: :
functionObjects::regionFunctionObject(name, runTime, dict), functionObjects::regionFunctionObject(name, runTime, dict),
PtrList<surfMeshSampler>(), PtrList<surfMeshSample>(),
mesh_(refCast<const fvMesh>(obr_)), mesh_(refCast<const fvMesh>(obr_)),
fieldSelection_() fieldSelection_(),
derivedNames_(),
sampleScheme_(word::null)
{ {
read(dict); read(dict);
} }
@ -122,10 +124,11 @@ Foam::surfMeshSamplers::surfMeshSamplers
) )
: :
functionObjects::regionFunctionObject(name, obr, dict), functionObjects::regionFunctionObject(name, obr, dict),
PtrList<surfMeshSampler>(), PtrList<surfMeshSample>(),
mesh_(refCast<const fvMesh>(obr)), mesh_(refCast<const fvMesh>(obr)),
fieldSelection_(), fieldSelection_(),
derivedNames_() derivedNames_(),
sampleScheme_(word::null)
{ {
read(dict); read(dict);
} }
@ -141,125 +144,128 @@ void Foam::surfMeshSamplers::verbose(const bool verbosity)
bool Foam::surfMeshSamplers::execute() bool Foam::surfMeshSamplers::execute()
{ {
if (size()) if (empty())
{ {
const objectRegistry& db = mesh_.thisDb(); return true;
}
// Manage derived names const objectRegistry& db = mesh_.thisDb();
DynamicList<word> added(derivedNames_.size());
DynamicList<word> cleanup(derivedNames_.size());
for (const word& derivedName : derivedNames_) // Manage derived names
DynamicList<word> added(derivedNames_.size());
DynamicList<word> cleanup(derivedNames_.size());
for (const word& derivedName : derivedNames_)
{
if (derivedName == "rhoU")
{ {
if (derivedName == "rhoU") added.append(derivedName);
if (!db.foundObject<volVectorField>(derivedName))
{ {
added.append(derivedName); cleanup.append(derivedName);
if (!db.foundObject<volVectorField>(derivedName)) db.store
(
new volVectorField
(
derivedName,
// rhoU = rho * U
(
mesh_.lookupObject<volScalarField>("rho")
* mesh_.lookupObject<volVectorField>("U")
)
)
);
}
}
else if (derivedName == "pTotal")
{
added.append(derivedName);
if (!db.foundObject<volScalarField>(derivedName))
{
cleanup.append(derivedName);
const volScalarField& p =
mesh_.lookupObject<volScalarField>("p");
if (p.dimensions() == dimPressure)
{ {
cleanup.append(derivedName);
db.store db.store
( (
new volVectorField new volScalarField
( (
derivedName, derivedName,
// rhoU = rho * U // pTotal = p + rho U^2 / 2
( (
mesh_.lookupObject<volScalarField>("rho") p
* mesh_.lookupObject<volVectorField>("U") + 0.5
* mesh_.lookupObject<volScalarField>("rho")
* magSqr
(
mesh_.lookupObject<volVectorField>("U")
)
)
)
);
}
else
{
db.store
(
new volScalarField
(
derivedName,
// pTotal = p + U^2 / 2
(
p
+ 0.5
* magSqr
(
mesh_.lookupObject<volVectorField>("U")
)
) )
) )
); );
} }
} }
else if (derivedName == "pTotal")
{
added.append(derivedName);
if (!db.foundObject<volScalarField>(derivedName))
{
cleanup.append(derivedName);
const volScalarField& p =
mesh_.lookupObject<volScalarField>("p");
if (p.dimensions() == dimPressure)
{
db.store
(
new volScalarField
(
derivedName,
// pTotal = p + rho U^2 / 2
(
p
+ 0.5
* mesh_.lookupObject<volScalarField>("rho")
* magSqr
(
mesh_.lookupObject<volVectorField>("U")
)
)
)
);
}
else
{
db.store
(
new volScalarField
(
derivedName,
// pTotal = p + U^2 / 2
(
p
+ 0.5
* magSqr
(
mesh_.lookupObject<volVectorField>("U")
)
)
)
);
}
}
}
else
{
WarningInFunction
<< "unknown derived name: " << derivedName << nl
<< "Use one of 'rhoU', 'pTotal'" << nl
<< endl;
}
} }
else
// The acceptable fields
wordHashSet acceptable(added);
acceptable.insertMany(acceptType<scalar>());
acceptable.insertMany(acceptType<vector>());
acceptable.insertMany(acceptType<sphericalTensor>());
acceptable.insertMany(acceptType<symmTensor>());
acceptable.insertMany(acceptType<tensor>());
const wordList fields = acceptable.sortedToc();
if (!fields.empty())
{ {
for (surfMeshSampler& s : surfaces()) WarningInFunction
{ << "unknown derived name: " << derivedName << nl
// Potentially monitor the update for writing geometry? << "Use one of 'rhoU', 'pTotal'" << nl
if (s.needsUpdate()) << endl;
{
s.update();
}
s.sample(fields);
}
} }
checkOutNames(db, cleanup);
} }
// The acceptable fields
wordHashSet acceptable(added);
acceptable.insertMany(acceptType<scalar>());
acceptable.insertMany(acceptType<vector>());
acceptable.insertMany(acceptType<sphericalTensor>());
acceptable.insertMany(acceptType<symmTensor>());
acceptable.insertMany(acceptType<tensor>());
const wordList fields = acceptable.sortedToc();
if (!fields.empty())
{
for (surfMeshSample& s : surfaces())
{
// Potentially monitor the update for writing geometry?
if (s.needsUpdate())
{
s.update();
}
s.sample(fields, sampleScheme_);
}
}
checkOutNames(db, cleanup);
return true; return true;
} }
@ -287,7 +293,7 @@ bool Foam::surfMeshSamplers::write()
// Avoid duplicate entries // Avoid duplicate entries
select.uniq(); select.uniq();
for (const surfMeshSampler& s : surfaces()) for (const surfMeshSample& s : surfaces())
{ {
s.write(select); s.write(select);
} }
@ -305,6 +311,8 @@ bool Foam::surfMeshSamplers::read(const dictionary& dict)
if (dict.found("surfaces")) if (dict.found("surfaces"))
{ {
sampleScheme_ = dict.lookupOrDefault<word>("sampleScheme", "cell");
dict.lookup("fields") >> fieldSelection_; dict.lookup("fields") >> fieldSelection_;
fieldSelection_.uniq(); fieldSelection_.uniq();
@ -316,10 +324,10 @@ bool Foam::surfMeshSamplers::read(const dictionary& dict)
} }
Info<< nl; Info<< nl;
PtrList<surfMeshSampler> newList PtrList<surfMeshSample> newList
( (
dict.lookup("surfaces"), dict.lookup("surfaces"),
surfMeshSampler::iNew(mesh_) surfMeshSample::iNew(mesh_)
); );
transfer(newList); transfer(newList);
@ -332,7 +340,7 @@ bool Foam::surfMeshSamplers::read(const dictionary& dict)
if (this->size()) if (this->size())
{ {
Info<< "Reading surface description:" << nl; Info<< "Reading surface description:" << nl;
for (surfMeshSampler& s : surfaces()) for (surfMeshSample& s : surfaces())
{ {
Info<< " " << s.name() << nl; Info<< " " << s.name() << nl;
if (createOnRead) if (createOnRead)
@ -383,7 +391,7 @@ void Foam::surfMeshSamplers::readUpdate(const polyMesh::readUpdateState state)
bool Foam::surfMeshSamplers::needsUpdate() const bool Foam::surfMeshSamplers::needsUpdate() const
{ {
for (const surfMeshSampler& s : surfaces()) for (const surfMeshSample& s : surfaces())
{ {
if (s.needsUpdate()) if (s.needsUpdate())
{ {
@ -399,7 +407,7 @@ bool Foam::surfMeshSamplers::expire()
{ {
bool justExpired = false; bool justExpired = false;
for (surfMeshSampler& s : surfaces()) for (surfMeshSample& s : surfaces())
{ {
if (s.expire()) if (s.expire())
{ {
@ -420,7 +428,7 @@ bool Foam::surfMeshSamplers::update()
} }
bool updated = false; bool updated = false;
for (surfMeshSampler& s : surfaces()) for (surfMeshSample& s : surfaces())
{ {
if (s.update()) if (s.update())
{ {

View File

@ -47,6 +47,9 @@ Description
// Fields to be sampled // Fields to be sampled
fields (p U); fields (p U);
// Scheme to obtain face centre value
sampleScheme cell;
// Optional: pre-defined derived fields to be sampled // Optional: pre-defined derived fields to be sampled
derived (rhoU pTotal); derived (rhoU pTotal);
@ -79,7 +82,7 @@ SourceFiles
#define surfMeshSamplers_H #define surfMeshSamplers_H
#include "regionFunctionObject.H" #include "regionFunctionObject.H"
#include "surfMeshSampler.H" #include "surfMeshSample.H"
#include "volFieldsFwd.H" #include "volFieldsFwd.H"
#include "surfaceFieldsFwd.H" #include "surfaceFieldsFwd.H"
#include "wordRes.H" #include "wordRes.H"
@ -102,7 +105,7 @@ class dictionary;
class surfMeshSamplers class surfMeshSamplers
: :
public functionObjects::regionFunctionObject, public functionObjects::regionFunctionObject,
public PtrList<surfMeshSampler> public PtrList<surfMeshSample>
{ {
// Static data members // Static data members
@ -124,6 +127,9 @@ class surfMeshSamplers
//- Names of derived fields to create and sample //- Names of derived fields to create and sample
wordList derivedNames_; wordList derivedNames_;
//- Sample scheme to obtain face values
word sampleScheme_;
// Private Member Functions // Private Member Functions
@ -135,15 +141,15 @@ class surfMeshSamplers
); );
//- Access the sampling surfaces //- Access the sampling surfaces
inline const PtrList<surfMeshSampler>& surfaces() const inline const PtrList<surfMeshSample>& surfaces() const
{ {
return static_cast<const PtrList<surfMeshSampler>&>(*this); return static_cast<const PtrList<surfMeshSample>&>(*this);
} }
//- Access the sampling surfaces //- Access the sampling surfaces
inline PtrList<surfMeshSampler>& surfaces() inline PtrList<surfMeshSample>& surfaces()
{ {
return static_cast<PtrList<surfMeshSampler>&>(*this); return static_cast<PtrList<surfMeshSample>&>(*this);
} }
@ -152,8 +158,10 @@ class surfMeshSamplers
wordList acceptType() const; wordList acceptType() const;
//- Disallow default bitwise copy construct and assignment //- No copy construct
surfMeshSamplers(const surfMeshSamplers&) = delete; surfMeshSamplers(const surfMeshSamplers&) = delete;
//- No copy assignment
void operator=(const surfMeshSamplers&) = delete; void operator=(const surfMeshSamplers&) = delete;

View File

@ -2,7 +2,7 @@
========= | ========= |
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration | \\ / O peration |
\\ / A nd | Copyright (C) 2016 OpenCFD Ltd. \\ / A nd | Copyright (C) 2016-2018 OpenCFD Ltd.
\\/ M anipulation | \\/ M anipulation |
------------------------------------------------------------------------------- -------------------------------------------------------------------------------
License License
@ -37,6 +37,7 @@ Foam::surfMeshSamplers::acceptType() const
return mesh_.names<VolFieldType>(fieldSelection_); return mesh_.names<VolFieldType>(fieldSelection_);
} }
#if 0 #if 0
template<class Type> template<class Type>
Foam::wordList Foam::wordList
@ -55,10 +56,8 @@ Foam::surfMeshSamplers::acceptType
return objects.names(VolFieldType::typeName, fieldSelection_); return objects.names(VolFieldType::typeName, fieldSelection_);
} }
else
{ return mesh_.names<VolFieldType>(fieldSelection_);
return mesh_.names<VolFieldType>(fieldSelection_);
}
} }
#endif #endif

View File

@ -23,7 +23,7 @@ License
\*---------------------------------------------------------------------------*/ \*---------------------------------------------------------------------------*/
#include "surfMeshDiscreteSampler.H" #include "surfMeshSampleDiscrete.H"
#include "MeshedSurfaces.H" #include "MeshedSurfaces.H"
#include "addToRunTimeSelectionTable.H" #include "addToRunTimeSelectionTable.H"
@ -32,14 +32,14 @@ License
namespace Foam namespace Foam
{ {
defineTypeNameAndDebug(surfMeshDiscreteSampler, 0); defineTypeNameAndDebug(surfMeshSampleDiscrete, 0);
// Add under name "sampledTriSurfaceMesh" // Add under name "sampledTriSurfaceMesh"
// for symmetry with normal sampledSurface // for symmetry with regular sampledSurface
addNamedToRunTimeSelectionTable addNamedToRunTimeSelectionTable
( (
surfMeshSampler, surfMeshSample,
surfMeshDiscreteSampler, surfMeshSampleDiscrete,
word, word,
sampledTriSurfaceMesh sampledTriSurfaceMesh
); );
@ -48,18 +48,18 @@ namespace Foam
// * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * // // * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * //
void Foam::surfMeshDiscreteSampler::transferContent() void Foam::surfMeshSampleDiscrete::transferContent()
{ {
SurfaceSource& src = static_cast<SurfaceSource&>(*this); getOrCreateSurfMesh().transfer
surfMesh& dst = getOrCreateSurfMesh(); (
static_cast<SurfaceSource&>(*this)
dst.transfer(src); );
} }
// * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * // // * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * //
Foam::surfMeshDiscreteSampler::surfMeshDiscreteSampler Foam::surfMeshSampleDiscrete::surfMeshSampleDiscrete
( (
const word& name, const word& name,
const polyMesh& mesh, const polyMesh& mesh,
@ -67,24 +67,24 @@ Foam::surfMeshDiscreteSampler::surfMeshDiscreteSampler
const discreteSurface::samplingSource sampleSource const discreteSurface::samplingSource sampleSource
) )
: :
surfMeshSampler(name, mesh), surfMeshSample(name, mesh),
SurfaceSource(mesh, surfaceName, sampleSource, false) // no interpolate SurfaceSource(mesh, surfaceName, sampleSource, false) // no interpolate
{} {}
Foam::surfMeshDiscreteSampler::surfMeshDiscreteSampler Foam::surfMeshSampleDiscrete::surfMeshSampleDiscrete
( (
const word& name, const word& name,
const polyMesh& mesh, const polyMesh& mesh,
const dictionary& dict const dictionary& dict
) )
: :
surfMeshSampler(name, mesh), surfMeshSample(name, mesh),
SurfaceSource(mesh, dict, false) // no interpolate SurfaceSource(mesh, dict, false) // no interpolate
{} {}
Foam::surfMeshDiscreteSampler::surfMeshDiscreteSampler Foam::surfMeshSampleDiscrete::surfMeshSampleDiscrete
( (
const word& name, const word& name,
const polyMesh& mesh, const polyMesh& mesh,
@ -92,32 +92,26 @@ Foam::surfMeshDiscreteSampler::surfMeshDiscreteSampler
const word& sampleSourceName const word& sampleSourceName
) )
: :
surfMeshSampler(name, mesh), surfMeshSample(name, mesh),
SurfaceSource(name, mesh, surface, sampleSourceName, false) SurfaceSource(name, mesh, surface, sampleSourceName, false)
{} {}
// * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * //
Foam::surfMeshDiscreteSampler::~surfMeshDiscreteSampler()
{}
// * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * // // * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
bool Foam::surfMeshDiscreteSampler::needsUpdate() const bool Foam::surfMeshSampleDiscrete::needsUpdate() const
{ {
return SurfaceSource::needsUpdate(); return SurfaceSource::needsUpdate();
} }
bool Foam::surfMeshDiscreteSampler::expire() bool Foam::surfMeshSampleDiscrete::expire()
{ {
return SurfaceSource::expire(); return SurfaceSource::expire();
} }
bool Foam::surfMeshDiscreteSampler::update() bool Foam::surfMeshSampleDiscrete::update()
{ {
if (SurfaceSource::update()) if (SurfaceSource::update())
{ {
@ -129,7 +123,7 @@ bool Foam::surfMeshDiscreteSampler::update()
} }
bool Foam::surfMeshDiscreteSampler::update(const treeBoundBox& bb) bool Foam::surfMeshSampleDiscrete::update(const treeBoundBox& bb)
{ {
if (SurfaceSource::update(bb)) if (SurfaceSource::update(bb))
{ {
@ -141,18 +135,19 @@ bool Foam::surfMeshDiscreteSampler::update(const treeBoundBox& bb)
} }
bool Foam::surfMeshDiscreteSampler::sample bool Foam::surfMeshSampleDiscrete::sample
( (
const word& fieldName const word& fieldName,
const word& sampleScheme
) const ) const
{ {
return return
( (
sampleType<scalar>(fieldName) sampleType<scalar>(fieldName, sampleScheme)
|| sampleType<vector>(fieldName) || sampleType<vector>(fieldName, sampleScheme)
|| sampleType<sphericalTensor>(fieldName) || sampleType<sphericalTensor>(fieldName, sampleScheme)
|| sampleType<symmTensor>(fieldName) || sampleType<symmTensor>(fieldName, sampleScheme)
|| sampleType<tensor>(fieldName) || sampleType<tensor>(fieldName, sampleScheme)
); );
} }

View File

@ -22,23 +22,47 @@ License
along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>. along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>.
Class Class
Foam::surfMeshDiscreteSampler Foam::surfMeshSampleDiscrete
Description Description
Sampling surfFields onto a surfMesh based on a triSurfaceMesh. Sampling surfFields onto a surfMesh based on a triSurfaceMesh.
This is often embedded as part of a surfMeshSamplers function object.
Usage
Example of function object partial specification:
\verbatim
surfaces
(
surface1
{
type sampledTriSurfaceMesh;
surface something.obj;
source cells;
}
);
\endverbatim
Where the sub-entries comprise:
\table
Property | Description | Required | Default
type | sampledTriSurfaceMesh | yes |
surface | surface name in triSurface/ | yes |
source | cells/insideCells/boundaryFaces | yes |
\endtable
See Also See Also
discreteSurface, surfMeshSampler discreteSurface, surfMeshSample
SourceFiles SourceFiles
surfMeshDiscreteSampler.C surfMeshSampleDiscrete.C
\*---------------------------------------------------------------------------*/ \*---------------------------------------------------------------------------*/
#ifndef surfMeshDiscreteSampler_H #ifndef surfMeshSampleDiscrete_H
#define surfMeshDiscreteSampler_H #define surfMeshSampleDiscrete_H
#include "surfMeshSampler.H" #include "surfMeshSample.H"
#include "discreteSurface.H" #include "discreteSurface.H"
#include "triSurfaceMesh.H" #include "triSurfaceMesh.H"
@ -47,15 +71,15 @@ SourceFiles
namespace Foam namespace Foam
{ {
class surfMeshDiscreteSampler; class surfMeshSampleDiscrete;
/*---------------------------------------------------------------------------*\ /*---------------------------------------------------------------------------*\
Class surfMeshDiscreteSampler Declaration Class surfMeshSampleDiscrete Declaration
\*---------------------------------------------------------------------------*/ \*---------------------------------------------------------------------------*/
class surfMeshDiscreteSampler class surfMeshSampleDiscrete
: :
public surfMeshSampler, public surfMeshSample,
private discreteSurface private discreteSurface
{ {
// Private typedefs for convenience // Private typedefs for convenience
@ -67,16 +91,25 @@ class surfMeshDiscreteSampler
//- Transfer mesh content from SurfaceSource to surfMesh //- Transfer mesh content from SurfaceSource to surfMesh
void transferContent(); void transferContent();
//- Sample field on surface.
template<class Type>
bool sampleType
(
const word& fieldName,
const word& sampleScheme
) const;
public: public:
//- Runtime type information //- Runtime type information
TypeName("surfMeshDiscreteSampler"); TypeName("surfMeshSampleDiscrete");
// Constructors // Constructors
//- Construct from components //- Construct from components
surfMeshDiscreteSampler surfMeshSampleDiscrete
( (
const word& name, const word& name,
const polyMesh& mesh, const polyMesh& mesh,
@ -85,7 +118,7 @@ public:
); );
//- Construct from dictionary //- Construct from dictionary
surfMeshDiscreteSampler surfMeshSampleDiscrete
( (
const word& name, const word& name,
const polyMesh& mesh, const polyMesh& mesh,
@ -93,7 +126,7 @@ public:
); );
//- Construct from triSurface //- Construct from triSurface
surfMeshDiscreteSampler surfMeshSampleDiscrete
( (
const word& name, const word& name,
const polyMesh& mesh, const polyMesh& mesh,
@ -103,7 +136,7 @@ public:
//- Destructor //- Destructor
virtual ~surfMeshDiscreteSampler(); virtual ~surfMeshSampleDiscrete() = default;
// Member Functions // Member Functions
@ -123,15 +156,14 @@ public:
//- Update the surface using a bound box to limit the searching. //- Update the surface using a bound box to limit the searching.
// For direct use, i.e. not through sample. // For direct use, i.e. not through sample.
// Do nothing (and return false) if no update was needed // Do nothing (and return false) if no update was needed
bool update(const treeBoundBox&); bool update(const treeBoundBox& bb);
//- Sample the volume field onto surface //- Sample the volume field onto surface
virtual bool sample(const word& fieldName) const; virtual bool sample
(
//- Sample field on surface. const word& fieldName,
template<class Type> const word& sampleScheme = "cell"
bool sampleType(const word& fieldName) const; ) const;
}; };
@ -143,7 +175,7 @@ public:
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
#ifdef NoRepository #ifdef NoRepository
#include "surfMeshDiscreteSamplerTemplates.C" #include "surfMeshSampleDiscreteTemplates.C"
#endif #endif
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //

View File

@ -23,31 +23,33 @@ License
\*---------------------------------------------------------------------------*/ \*---------------------------------------------------------------------------*/
#include "surfMeshDiscreteSampler.H" #include "surfMeshSampleDiscrete.H"
#include "dimensionedType.H" #include "dimensionedType.H"
#include "error.H" #include "error.H"
// * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * // // * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * //
template<class Type> template<class Type>
bool Foam::surfMeshDiscreteSampler::sampleType bool Foam::surfMeshSampleDiscrete::sampleType
( (
const word& fieldName const word& fieldName,
const word& sampleScheme
) const ) const
{ {
typedef GeometricField<Type, fvPatchField, volMesh> VolFieldType; typedef GeometricField<Type, fvPatchField, volMesh> VolFieldType;
const polyMesh& mesh = SurfaceSource::mesh(); const auto volFldPtr =
SurfaceSource::mesh().lookupObjectPtr<VolFieldType>(fieldName);
if (!mesh.foundObject<VolFieldType>(fieldName)) if (!volFldPtr)
{ {
return false; return false;
} }
const VolFieldType& fld = mesh.lookupObject<VolFieldType>(fieldName); auto samplerPtr = interpolation<Type>::New(sampleScheme, *volFldPtr);
getOrCreateSurfField<Type>(fld).field() getOrCreateSurfField<Type>(*volFldPtr).field()
= SurfaceSource::sampleField(fld); = SurfaceSource::sampleOnFaces(*samplerPtr);
return true; return true;
} }
@ -55,14 +57,14 @@ bool Foam::surfMeshDiscreteSampler::sampleType
// template<class Type> // template<class Type>
// Foam::tmp<Foam::DimensionedField<Type, Foam::surfGeoMesh>> // Foam::tmp<Foam::DimensionedField<Type, Foam::surfGeoMesh>>
// Foam::surfMeshDiscreteSampler::sampleField // Foam::surfMeshSampleDiscrete::sampleOnFaces
// ( // (
// const GeometricField<Type, fvPatchField, volMesh>& fld // const GeometricField<Type, fvPatchField, volMesh>& fld
// ) const // ) const
// { // {
// typedef DimensionedField<Type, surfGeoMesh> SurfFieldType; // typedef DimensionedField<Type, surfGeoMesh> SurfFieldType;
// //
// tmp<Field<Type>> tfield = SurfaceSource::sampleField(fld); // tmp<Field<Type>> tfield = SurfaceSource::sampleOnFaces(fld);
// SurfFieldType& result = getOrCreateSurfField<Type>(fld); // SurfFieldType& result = getOrCreateSurfField<Type>(fld);
// //
// // need to verify if this will be needed (in the future) // // need to verify if this will be needed (in the future)
@ -72,7 +74,7 @@ bool Foam::surfMeshDiscreteSampler::sampleType
// // maybe resampling changed the surfMesh, // // maybe resampling changed the surfMesh,
// // but the existing surfField wasn't updated // // but the existing surfField wasn't updated
// //
// result.setSize(s.size(), Zero); // result.resize(s.size(), Zero);
// } // }
// //
// if (result.size() != sampleElements().size()) // if (result.size() != sampleElements().size())

View File

@ -3,7 +3,7 @@
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration | \\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation \\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\/ M anipulation | \\/ M anipulation | Copyright (C) 2018 OpenCFD Ltd.
------------------------------------------------------------------------------- -------------------------------------------------------------------------------
License License
This file is part of OpenFOAM. This file is part of OpenFOAM.
@ -37,6 +37,7 @@ static const Foam::scalar zeroish = Foam::SMALL;
static const Foam::scalar positive = Foam::SMALL * 1E3; static const Foam::scalar positive = Foam::SMALL * 1E3;
//! \endcond //! \endcond
// * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * // // * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * //
void Foam::cuttingPlane::calcCutCells void Foam::cuttingPlane::calcCutCells
@ -105,9 +106,9 @@ void Foam::cuttingPlane::intersectEdges
DynamicList<point> dynCuttingPoints(4*meshCells_.size()); DynamicList<point> dynCuttingPoints(4*meshCells_.size());
forAll(edges, edgeI) forAll(edges, edgei)
{ {
const edge& e = edges[edgeI]; const edge& e = edges[edgei];
if if
( (
@ -116,7 +117,7 @@ void Foam::cuttingPlane::intersectEdges
) )
{ {
// Edge is cut // Edge is cut
edgePoint[edgeI] = dynCuttingPoints.size(); edgePoint[edgei] = dynCuttingPoints.size();
const point& p0 = points[e[0]]; const point& p0 = points[e[0]];
const point& p1 = points[e[1]]; const point& p1 = points[e[1]];
@ -138,7 +139,7 @@ void Foam::cuttingPlane::intersectEdges
} }
else else
{ {
edgePoint[edgeI] = -1; edgePoint[edgei] = -1;
} }
} }
@ -151,48 +152,48 @@ bool Foam::cuttingPlane::walkCell
const primitiveMesh& mesh, const primitiveMesh& mesh,
const labelUList& edgePoint, const labelUList& edgePoint,
const label celli, const label celli,
const label startEdgeI, const label startEdgei,
DynamicList<label>& faceVerts DynamicList<label>& faceVerts
) )
{ {
label facei = -1; label facei = -1;
label edgeI = startEdgeI; label edgei = startEdgei;
label nIter = 0; label nIter = 0;
faceVerts.clear(); faceVerts.clear();
do do
{ {
faceVerts.append(edgePoint[edgeI]); faceVerts.append(edgePoint[edgei]);
// Cross edge to other face // Cross edge to other face
facei = meshTools::otherFace(mesh, celli, facei, edgeI); facei = meshTools::otherFace(mesh, celli, facei, edgei);
// Find next cut edge on face. // Find next cut edge on face.
const labelList& fEdges = mesh.faceEdges()[facei]; const labelList& fEdges = mesh.faceEdges()[facei];
label nextEdgeI = -1; label nextEdgei = -1;
//Note: here is where we should check for whether there are more //Note: here is where we should check for whether there are more
// than 2 intersections with the face (warped/non-convex face). // than 2 intersections with the face (warped/non-convex face).
// If so should e.g. decompose the cells on both faces and redo // If so should e.g. decompose the cells on both faces and redo
// the calculation. // the calculation.
for (const label edge2I : fEdges) for (const label edge2i : fEdges)
{ {
if (edge2I != edgeI && edgePoint[edge2I] != -1) if (edge2i != edgei && edgePoint[edge2i] != -1)
{ {
nextEdgeI = edge2I; nextEdgei = edge2i;
break; break;
} }
} }
if (nextEdgeI == -1) if (nextEdgei == -1)
{ {
// Did not find another cut edge on facei. Do what? // Did not find another cut edge on facei. Do what?
WarningInFunction WarningInFunction
<< "Did not find closed walk along surface of cell " << celli << "Did not find closed walk along surface of cell " << celli
<< " starting from edge " << startEdgeI << " starting from edge " << startEdgei
<< " in " << nIter << " iterations." << nl << " in " << nIter << " iterations." << nl
<< "Collected cutPoints so far:" << faceVerts << "Collected cutPoints so far:" << faceVerts
<< endl; << endl;
@ -200,7 +201,7 @@ bool Foam::cuttingPlane::walkCell
return false; return false;
} }
edgeI = nextEdgeI; edgei = nextEdgei;
++nIter; ++nIter;
@ -209,13 +210,13 @@ bool Foam::cuttingPlane::walkCell
WarningInFunction WarningInFunction
<< "Did not find closed walk along surface of cell " << celli << "Did not find closed walk along surface of cell " << celli
<< " at " << mesh.cellCentres()[celli] << " at " << mesh.cellCentres()[celli]
<< " starting from edge " << startEdgeI << " starting from edge " << startEdgei
<< " in " << nIter << " iterations." << " in " << nIter << " iterations."
<< endl; << endl;
return false; return false;
} }
} while (edgeI != startEdgeI); } while (edgei != startEdgei);
if (faceVerts.size() >= 3) if (faceVerts.size() >= 3)
@ -225,7 +226,7 @@ bool Foam::cuttingPlane::walkCell
WarningInFunction WarningInFunction
<< "Did not find closed walk along surface of cell " << celli << "Did not find closed walk along surface of cell " << celli
<< " starting from edge " << startEdgeI << nl << " starting from edge " << startEdgei << nl
<< "Collected cutPoints so far:" << faceVerts << "Collected cutPoints so far:" << faceVerts
<< endl; << endl;
@ -254,19 +255,19 @@ void Foam::cuttingPlane::walkCellCuts
// Find the starting edge to walk from. // Find the starting edge to walk from.
const labelList& cEdges = mesh.cellEdges()[celli]; const labelList& cEdges = mesh.cellEdges()[celli];
label startEdgeI = -1; label startEdgei = -1;
for (const label edgeI : cEdges) for (const label edgei : cEdges)
{ {
if (edgePoint[edgeI] != -1) if (edgePoint[edgei] != -1)
{ {
startEdgeI = edgeI; startEdgei = edgei;
break; break;
} }
} }
// Check for the unexpected ... // Check for the unexpected ...
if (startEdgeI == -1) if (startEdgei == -1)
{ {
FatalErrorInFunction FatalErrorInFunction
<< "Cannot find cut edge for cut cell " << celli << "Cannot find cut edge for cut cell " << celli
@ -279,7 +280,7 @@ void Foam::cuttingPlane::walkCellCuts
mesh, mesh,
edgePoint, edgePoint,
celli, celli,
startEdgeI, startEdgei,
faceVerts faceVerts
); );
@ -379,7 +380,6 @@ void Foam::cuttingPlane::remapFaces
const labelUList& faceMap const labelUList& faceMap
) )
{ {
// Recalculate the cells cut
if (notNull(faceMap) && faceMap.size()) if (notNull(faceMap) && faceMap.size())
{ {
MeshStorage::remapFaces(faceMap); MeshStorage::remapFaces(faceMap);

View File

@ -55,7 +55,7 @@ namespace Foam
class primitiveMesh; class primitiveMesh;
/*---------------------------------------------------------------------------*\ /*---------------------------------------------------------------------------*\
Class cuttingPlane Declaration Class cuttingPlane Declaration
\*---------------------------------------------------------------------------*/ \*---------------------------------------------------------------------------*/
class cuttingPlane class cuttingPlane
@ -98,7 +98,7 @@ class cuttingPlane
const primitiveMesh&, const primitiveMesh&,
const labelUList& edgePoint, const labelUList& edgePoint,
const label celli, const label celli,
const label startEdgeI, const label startEdgei,
DynamicList<label>& faceVerts DynamicList<label>& faceVerts
); );
@ -138,7 +138,7 @@ public:
// Constructors // Constructors
//- Construct from plane and mesh reference, //- Construct from plane and mesh reference,
// possibly restricted to a list of cells //- possibly restricted to a list of cells
cuttingPlane cuttingPlane
( (
const plane& pln, const plane& pln,
@ -150,31 +150,30 @@ public:
// Member Functions // Member Functions
//- Return plane used //- Return the plane used
const plane& planeDesc() const const plane& planeDesc() const
{ {
return static_cast<const plane&>(*this); return static_cast<const plane&>(*this);
} }
//- Return List of cells cut by the plane //- The mesh cells cut by the plane
const labelList& meshCells() const const labelList& meshCells() const
{ {
return meshCells_; return meshCells_;
} }
//- Return true or false to question: have any cells been cut? //- The mesh cells cut by the plane
labelList& meshCells()
{
return meshCells_;
}
//- Have any cells been cut?
bool cut() const bool cut() const
{ {
return meshCells_.size(); return meshCells_.size();
} }
//- Sample the cell field
template<class Type>
tmp<Field<Type>> sample(const Field<Type>&) const;
template<class Type>
tmp<Field<Type>> sample(const tmp<Field<Type>>&) const;
// Member Operators // Member Operators
@ -189,12 +188,6 @@ public:
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
#ifdef NoRepository
#include "cuttingPlaneTemplates.C"
#endif
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
#endif #endif
// ************************************************************************* // // ************************************************************************* //

View File

@ -3,7 +3,7 @@
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration | \\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation \\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\/ M anipulation | Copyright (C) 2016-2017 OpenCFD Ltd. \\/ M anipulation | Copyright (C) 2016-2018 OpenCFD Ltd.
------------------------------------------------------------------------------- -------------------------------------------------------------------------------
License License
This file is part of OpenFOAM. This file is part of OpenFOAM.
@ -36,26 +36,105 @@ License
namespace Foam namespace Foam
{ {
defineTypeNameAndDebug(distanceSurface, 0); defineTypeNameAndDebug(distanceSurface, 0);
addToRunTimeSelectionTable(sampledSurface, distanceSurface, word);
} }
// * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * //
// * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * //
Foam::distanceSurface::distanceSurface
(
const word& defaultSurfaceName,
const polyMesh& mesh,
const dictionary& dict
)
:
mesh_(mesh),
surfPtr_
(
searchableSurface::New
(
dict.lookup("surfaceType"),
IOobject
(
dict.lookupOrDefault("surfaceName", defaultSurfaceName),
mesh.time().constant(), // directory
"triSurface", // instance
mesh.time(), // registry
IOobject::MUST_READ,
IOobject::NO_WRITE
),
dict
)
),
distance_(readScalar(dict.lookup("distance"))),
signed_(readBool(dict.lookup("signed"))),
cell_(dict.lookupOrDefault("cell", true)),
regularise_(dict.lookupOrDefault("regularise", true)),
bounds_(dict.lookupOrDefault("bounds", boundBox::invertedBox)),
zoneKey_(keyType::null),
isoSurfCellPtr_(nullptr),
isoSurfPtr_(nullptr)
{}
Foam::distanceSurface::distanceSurface
(
const polyMesh& mesh,
const bool interpolate,
const word& surfaceType,
const word& surfaceName,
const scalar distance,
const bool signedDistance,
const bool cell,
const Switch regularise,
const boundBox& bounds
)
:
mesh_(mesh),
surfPtr_
(
searchableSurface::New
(
surfaceType,
IOobject
(
surfaceName, // name
mesh.time().constant(), // directory
"triSurface", // instance
mesh.time(), // registry
IOobject::MUST_READ,
IOobject::NO_WRITE
),
dictionary()
)
),
distance_(distance),
signed_(signedDistance),
cell_(cell),
regularise_(regularise),
bounds_(bounds),
zoneKey_(keyType::null),
isoSurfCellPtr_(nullptr),
isoSurfPtr_(nullptr)
{}
// * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
void Foam::distanceSurface::createGeometry() void Foam::distanceSurface::createGeometry()
{ {
if (debug) if (debug)
{ {
Pout<< "distanceSurface::createGeometry :updating geometry." << endl; Pout<< "distanceSurface::createGeometry updating geometry." << endl;
} }
// Clear any stored topologies // Clear any stored topologies
isoSurfCellPtr_.clear(); isoSurfCellPtr_.clear();
isoSurfPtr_.clear(); isoSurfPtr_.clear();
// Clear derived data const fvMesh& fvm = static_cast<const fvMesh&>(mesh_);
clearGeom();
const fvMesh& fvm = static_cast<const fvMesh&>(mesh()); const labelList& own = fvm.faceOwner();
// Distance to cell centres // Distance to cell centres
// ~~~~~~~~~~~~~~~~~~~~~~~~ // ~~~~~~~~~~~~~~~~~~~~~~~~
@ -77,7 +156,7 @@ void Foam::distanceSurface::createGeometry()
dimensionedScalar(dimLength, Zero) dimensionedScalar(dimLength, Zero)
) )
); );
volScalarField& cellDistance = cellDistancePtr_(); volScalarField& cellDistance = *cellDistancePtr_;
// Internal field // Internal field
{ {
@ -110,10 +189,17 @@ void Foam::distanceSurface::createGeometry()
{ {
fld[i] = -Foam::mag(cc[i] - nearest[i].hitPoint()); fld[i] = -Foam::mag(cc[i] - nearest[i].hitPoint());
} }
else if (vT == volumeType::UNKNOWN)
{
// Treat as very far outside
fld[i] = GREAT;
}
else else
{ {
FatalErrorInFunction FatalErrorInFunction
<< "getVolumeType failure, neither INSIDE or OUTSIDE" << "getVolumeType failure:"
<< " neither INSIDE or OUTSIDE but "
<< volumeType::names[vT]
<< exit(FatalError); << exit(FatalError);
} }
} }
@ -137,6 +223,9 @@ void Foam::distanceSurface::createGeometry()
const pointField& cc = fvm.C().boundaryField()[patchi]; const pointField& cc = fvm.C().boundaryField()[patchi];
fvPatchScalarField& fld = cellDistanceBf[patchi]; fvPatchScalarField& fld = cellDistanceBf[patchi];
const label patchStarti = fvm.boundaryMesh()[patchi].start();
List<pointIndexHit> nearest; List<pointIndexHit> nearest;
surfPtr_().findNearest surfPtr_().findNearest
( (
@ -163,11 +252,23 @@ void Foam::distanceSurface::createGeometry()
{ {
fld[i] = -Foam::mag(cc[i] - nearest[i].hitPoint()); fld[i] = -Foam::mag(cc[i] - nearest[i].hitPoint());
} }
else if (vT == volumeType::UNKNOWN)
{
// Nothing known, so use the cell value.
// - this avoids spurious changes on the boundary
// The cell value
const label meshFacei = i+patchStarti;
const scalar& cellVal = cellDistance[own[meshFacei]];
fld[i] = cellVal;
}
else else
{ {
FatalErrorInFunction FatalErrorInFunction
<< "getVolumeType failure, " << "getVolumeType failure:"
<< "neither INSIDE or OUTSIDE" << " neither INSIDE or OUTSIDE but "
<< volumeType::names[vT]
<< exit(FatalError); << exit(FatalError);
} }
} }
@ -220,10 +321,17 @@ void Foam::distanceSurface::createGeometry()
pointDistance_[i] = pointDistance_[i] =
-Foam::mag(pts[i] - nearest[i].hitPoint()); -Foam::mag(pts[i] - nearest[i].hitPoint());
} }
else if (vT == volumeType::UNKNOWN)
{
// Treat as very far outside
pointDistance_[i] = GREAT;
}
else else
{ {
FatalErrorInFunction FatalErrorInFunction
<< "getVolumeType failure, neither INSIDE or OUTSIDE" << "getVolumeType failure:"
<< " neither INSIDE or OUTSIDE but "
<< volumeType::names[vT]
<< exit(FatalError); << exit(FatalError);
} }
} }
@ -263,7 +371,7 @@ void Foam::distanceSurface::createGeometry()
} }
//- Direct from cell field and point field. // Direct from cell field and point field.
if (cell_) if (cell_)
{ {
isoSurfCellPtr_.reset isoSurfCellPtr_.reset
@ -302,253 +410,12 @@ void Foam::distanceSurface::createGeometry()
} }
// * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * //
Foam::distanceSurface::distanceSurface
(
const word& name,
const polyMesh& mesh,
const dictionary& dict
)
:
sampledSurface(name, mesh, dict),
surfPtr_
(
searchableSurface::New
(
dict.lookup("surfaceType"),
IOobject
(
dict.lookupOrDefault("surfaceName", name), // name
mesh.time().constant(), // directory
"triSurface", // instance
mesh.time(), // registry
IOobject::MUST_READ,
IOobject::NO_WRITE
),
dict
)
),
distance_(readScalar(dict.lookup("distance"))),
signed_(readBool(dict.lookup("signed"))),
cell_(dict.lookupOrDefault("cell", true)),
regularise_(dict.lookupOrDefault("regularise", true)),
average_(dict.lookupOrDefault("average", false)),
bounds_(dict.lookupOrDefault("bounds", boundBox::invertedBox)),
zoneKey_(keyType::null),
needsUpdate_(true),
isoSurfCellPtr_(nullptr),
isoSurfPtr_(nullptr)
{
// dict.readIfPresent("zone", zoneKey_);
//
// if (debug && zoneKey_.size() && mesh.cellZones().findZoneID(zoneKey_) < 0)
// {
// Info<< "cellZone " << zoneKey_
// << " not found - using entire mesh" << endl;
// }
}
Foam::distanceSurface::distanceSurface
(
const word& name,
const polyMesh& mesh,
const bool interpolate,
const word& surfaceType,
const word& surfaceName,
const scalar distance,
const bool signedDistance,
const bool cell,
const Switch regularise,
const Switch average,
const boundBox& bounds
)
:
sampledSurface(name, mesh, interpolate),
surfPtr_
(
searchableSurface::New
(
surfaceType,
IOobject
(
surfaceName, // name
mesh.time().constant(), // directory
"triSurface", // instance
mesh.time(), // registry
IOobject::MUST_READ,
IOobject::NO_WRITE
),
dictionary()
)
),
distance_(distance),
signed_(signedDistance),
cell_(cell),
regularise_(regularise),
average_(average),
bounds_(bounds),
zoneKey_(keyType::null),
needsUpdate_(true),
isoSurfCellPtr_(nullptr),
isoSurfPtr_(nullptr)
{}
// * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * //
Foam::distanceSurface::~distanceSurface()
{}
// * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
bool Foam::distanceSurface::needsUpdate() const
{
return needsUpdate_;
}
bool Foam::distanceSurface::expire()
{
if (debug)
{
Pout<< "distanceSurface::expire :"
<< " needsUpdate:" << needsUpdate_ << endl;
}
// Clear derived data
clearGeom();
// already marked as expired
if (needsUpdate_)
{
return false;
}
needsUpdate_ = true;
return true;
}
bool Foam::distanceSurface::update()
{
if (debug)
{
Pout<< "distanceSurface::update :"
<< " needsUpdate:" << needsUpdate_ << endl;
}
if (!needsUpdate_)
{
return false;
}
createGeometry();
needsUpdate_ = false;
return true;
}
Foam::tmp<Foam::scalarField> Foam::distanceSurface::sample
(
const volScalarField& vField
) const
{
return sampleField(vField);
}
Foam::tmp<Foam::vectorField> Foam::distanceSurface::sample
(
const volVectorField& vField
) const
{
return sampleField(vField);
}
Foam::tmp<Foam::sphericalTensorField> Foam::distanceSurface::sample
(
const volSphericalTensorField& vField
) const
{
return sampleField(vField);
}
Foam::tmp<Foam::symmTensorField> Foam::distanceSurface::sample
(
const volSymmTensorField& vField
) const
{
return sampleField(vField);
}
Foam::tmp<Foam::tensorField> Foam::distanceSurface::sample
(
const volTensorField& vField
) const
{
return sampleField(vField);
}
Foam::tmp<Foam::scalarField> Foam::distanceSurface::interpolate
(
const interpolation<scalar>& interpolator
) const
{
return interpolateField(interpolator);
}
Foam::tmp<Foam::vectorField> Foam::distanceSurface::interpolate
(
const interpolation<vector>& interpolator
) const
{
return interpolateField(interpolator);
}
Foam::tmp<Foam::sphericalTensorField> Foam::distanceSurface::interpolate
(
const interpolation<sphericalTensor>& interpolator
) const
{
return interpolateField(interpolator);
}
Foam::tmp<Foam::symmTensorField> Foam::distanceSurface::interpolate
(
const interpolation<symmTensor>& interpolator
) const
{
return interpolateField(interpolator);
}
Foam::tmp<Foam::tensorField> Foam::distanceSurface::interpolate
(
const interpolation<tensor>& interpolator
) const
{
return interpolateField(interpolator);
}
void Foam::distanceSurface::print(Ostream& os) const void Foam::distanceSurface::print(Ostream& os) const
{ {
os << "distanceSurface: " << name() << " :" os << " surface:" << surfaceName()
<< " surface:" << surfPtr_().name() << " distance:" << distance()
<< " distance:" << distance_ << " faces:" << surface().surfFaces().size()
<< " faces:" << faces().size() << " points:" << surface().points().size();
<< " points:" << points().size();
} }

View File

@ -0,0 +1,236 @@
/*---------------------------------------------------------------------------*\
========= |
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\/ M anipulation | Copyright (C) 2016-2018 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 <http://www.gnu.org/licenses/>.
Class
Foam::distanceSurface
Description
A surface defined by distance to an input surface - using either
an isoSurfaceCell or an isoSurface.
Usage
Dictionary controls:
\table
Property | Description | Required | Default
distance | distance from surface | yes |
signed | apply sign for +ve/-ve distance | yes |
cell | use isoSurfaceCell algorithm | no | true
regularise | point snapping | yes |
bounds | limit with bounding box | no |
surfaceType | type of surface | yes |
surfaceName | name of surface in triSurface/ | no | dict name
\endtable
SourceFiles
distanceSurface.C
\*---------------------------------------------------------------------------*/
#ifndef distanceSurface_H
#define distanceSurface_H
#include "sampledSurface.H"
#include "searchableSurface.H"
#include "isoSurfaceCell.H"
#include "isoSurface.H"
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
namespace Foam
{
/*---------------------------------------------------------------------------*\
Class distanceSurface Declaration
\*---------------------------------------------------------------------------*/
class distanceSurface
{
// Private data
//- Reference to mesh
const polyMesh& mesh_;
//- Surface
const autoPtr<searchableSurface> surfPtr_;
//- Distance value
const scalar distance_;
//- Signed distance
const bool signed_;
//- Whether to use isoSurfaceCell or isoSurface
const bool cell_;
//- Whether to coarsen
const Switch regularise_;
//- Optional bounding box to trim triangles against
const boundBox bounds_;
//- If restricted to zones, name of this zone or a regular expression
keyType zoneKey_;
//- Distance to cell centres
autoPtr<volScalarField> cellDistancePtr_;
//- Distance to points
scalarField pointDistance_;
//- Constructed iso surface
autoPtr<isoSurfaceCell> isoSurfCellPtr_;
//- Constructed iso surface
autoPtr<isoSurface> isoSurfPtr_;
public:
//- Runtime type information
TypeName("distanceSurface");
// Constructors
//- Construct from dictionary
distanceSurface
(
const word& defaultSurfaceName,
const polyMesh& mesh,
const dictionary& dict
);
//- Construct from components
distanceSurface
(
const polyMesh& mesh,
const bool interpolate,
const word& surfaceType,
const word& surfaceName,
const scalar distance,
const bool signedDistance,
const bool cell,
const Switch regularise,
const boundBox& bounds = boundBox::invertedBox
);
//- Destructor
virtual ~distanceSurface() = default;
// Member Functions
//- Create/recreate the distance surface
void createGeometry();
//- The name of the underlying searchableSurface
const word& surfaceName() const
{
return surfPtr_->name();
}
//- The distance to the underlying searchableSurface
scalar distance() const
{
return distance_;
}
//- The underlying surface
const meshedSurface& surface() const
{
if (cell_)
{
return *isoSurfCellPtr_;
}
return *isoSurfPtr_;
}
//- The underlying surface
meshedSurface& surface()
{
if (cell_)
{
return *isoSurfCellPtr_;
}
return *isoSurfPtr_;
}
//- For each face, the original cell in mesh
const labelList& meshCells() const
{
if (cell_)
{
return isoSurfCellPtr_->meshCells();
}
return isoSurfPtr_->meshCells();
}
//- For each face, the original cell in mesh
labelList& meshCells()
{
if (cell_)
{
return isoSurfCellPtr_->meshCells();
}
return isoSurfPtr_->meshCells();
}
// Interpolate
//- Interpolate volume field onto surface points
template<class Type>
tmp<Field<Type>> interpolate
(
const GeometricField<Type, fvPatchField, volMesh>& cellValues,
const Field<Type>& pointValues
) const;
// Output
//- Print information
void print(Ostream& os) const;
};
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
} // End namespace Foam
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
#ifdef NoRepository
#include "distanceSurfaceTemplates.C"
#endif
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
#endif
// ************************************************************************* //

View File

@ -2,7 +2,7 @@
========= | ========= |
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration | \\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation \\ / A nd | Copyright (C) 2018 OpenCFD Ltd.
\\/ M anipulation | \\/ M anipulation |
------------------------------------------------------------------------------- -------------------------------------------------------------------------------
License License
@ -21,34 +21,29 @@ License
You should have received a copy of the GNU General Public License You should have received a copy of the GNU General Public License
along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>. along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>.
Description
Cutting plane sampling functionality
\*---------------------------------------------------------------------------*/ \*---------------------------------------------------------------------------*/
#include "cuttingPlane.H" #include "distanceSurface.H"
// * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * // // * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
template<class Type> template<class Type>
Foam::tmp<Foam::Field<Type>> Foam::cuttingPlane::sample Foam::tmp<Foam::Field<Type>>
Foam::distanceSurface::interpolate
( (
const Field<Type>& fld const GeometricField<Type, fvPatchField, volMesh>& cellValues,
const Field<Type>& pointValues
) const ) const
{ {
return tmp<Field<Type>>::New(fld, meshCells()); if (cell_)
{
return isoSurfCellPtr_().interpolate(cellValues, pointValues);
}
else
{
return isoSurfPtr_().interpolate(cellValues, pointValues);
}
} }
template<class Type>
Foam::tmp<Foam::Field<Type>> Foam::cuttingPlane::sample
(
const tmp<Field<Type>>& tfld
) const
{
tmp<Field<Type>> tsf = sample(tfld());
tfld.clear();
return tsf;
}
// ************************************************************************* // // ************************************************************************* //

View File

@ -36,7 +36,13 @@ License
namespace Foam namespace Foam
{ {
defineTypeNameAndDebug(isoSurface, 0); defineTypeNameAndDebug(isoSurface, 0);
}
// * * * * * * * * * * * * * * * Local Functions * * * * * * * * * * * * * * //
namespace Foam
{
// Helper class for slicing triangles // Helper class for slicing triangles
class storeOp class storeOp
{ {
@ -53,7 +59,16 @@ namespace Foam
tris_.append(tri); tris_.append(tri);
} }
}; };
}
// Avoid detecting change if the cells have been marked as GREAT
// (ie, ignore them)
static inline constexpr bool ignoreValue(const scalar val)
{
return (val >= 0.5*Foam::GREAT);
}
} // End namespace Foam
// * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * // // * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * //
@ -254,7 +269,7 @@ void Foam::isoSurface::syncUnseparatedPoints
forAll(pd.sharedPointLabels(), i) forAll(pd.sharedPointLabels(), i)
{ {
label meshPointi = pd.sharedPointLabels()[i]; const label meshPointi = pd.sharedPointLabels()[i];
// Fill my entries in the shared points // Fill my entries in the shared points
sharedPts[pd.sharedPointAddr()[i]] = pointValues[meshPointi]; sharedPts[pd.sharedPointAddr()[i]] = pointValues[meshPointi];
} }
@ -267,7 +282,7 @@ void Foam::isoSurface::syncUnseparatedPoints
// my local information. // my local information.
forAll(pd.sharedPointLabels(), i) forAll(pd.sharedPointLabels(), i)
{ {
label meshPointi = pd.sharedPointLabels()[i]; const label meshPointi = pd.sharedPointLabels()[i];
pointValues[meshPointi] = sharedPts[pd.sharedPointAddr()[i]]; pointValues[meshPointi] = sharedPts[pd.sharedPointAddr()[i]];
} }
} }
@ -280,16 +295,14 @@ Foam::scalar Foam::isoSurface::isoFraction
const scalar s1 const scalar s1
) const ) const
{ {
scalar d = s1-s0; const scalar d = s1-s0;
if (mag(d) > VSMALL) if (mag(d) > VSMALL)
{ {
return (iso_-s0)/d; return (iso_-s0)/d;
} }
else
{ return -1.0;
return -1.0;
}
} }
@ -301,19 +314,41 @@ bool Foam::isoSurface::isEdgeOfFaceCut
const bool neiLower const bool neiLower
) const ) const
{ {
// Could also count number of edges cut and return when they are > 1
// but doesn't appear to improve anything
forAll(f, fp) forAll(f, fp)
{ {
bool fpLower = (pVals[f[fp]] < iso_); const scalar& pt0Value = pVals[f[fp]];
if
( if (ignoreValue(pt0Value))
(fpLower != ownLower)
|| (fpLower != neiLower)
|| (fpLower != (pVals[f[f.fcIndex(fp)]] < iso_))
)
{ {
continue;
}
const bool fpLower = (pt0Value < iso_);
if (fpLower != ownLower || fpLower != neiLower)
{
// ++ncut;
return true; return true;
} }
else
{
const scalar& pt1Value = pVals[f[f.fcIndex(fp)]];
if (!ignoreValue(pt1Value) && (fpLower != (pt1Value < iso_)))
{
// ++ncut;
return true;
}
}
// if (ncut > 1)
// {
// return true;
// }
} }
return false; return false;
} }
@ -334,16 +369,16 @@ void Foam::isoSurface::getNeighbour
if (mesh_.isInternalFace(facei)) if (mesh_.isInternalFace(facei))
{ {
label nbr = (own[facei] == celli ? nei[facei] : own[facei]); const label nbr = (own[facei] == celli ? nei[facei] : own[facei]);
nbrValue = cVals[nbr]; nbrValue = cVals[nbr];
nbrPoint = meshC[nbr]; nbrPoint = meshC[nbr];
} }
else else
{ {
label bFacei = facei-mesh_.nInternalFaces(); const label bFacei = facei-mesh_.nInternalFaces();
label patchi = boundaryRegion[bFacei]; const label patchi = boundaryRegion[bFacei];
const polyPatch& pp = mesh_.boundaryMesh()[patchi]; const polyPatch& pp = mesh_.boundaryMesh()[patchi];
label patchFacei = facei-pp.start(); const label patchFacei = facei-pp.start();
nbrValue = cVals.boundaryField()[patchi][patchFacei]; nbrValue = cVals.boundaryField()[patchi][patchFacei];
nbrPoint = meshC.boundaryField()[patchi][patchFacei]; nbrPoint = meshC.boundaryField()[patchi][patchFacei];
@ -366,10 +401,18 @@ void Foam::isoSurface::calcCutTypes
faceCutType_.setSize(mesh_.nFaces()); faceCutType_.setSize(mesh_.nFaces());
faceCutType_ = NOTCUT; faceCutType_ = NOTCUT;
for (label facei = 0; facei < mesh_.nInternalFaces(); facei++) // Avoid detecting change if the cells have been marked as GREAT
// (ie, ignore them)
for (label facei = 0; facei < mesh_.nInternalFaces(); ++facei)
{ {
// CC edge. const scalar& ownValue = cVals[own[facei]];
bool ownLower = (cVals[own[facei]] < iso_); if (ignoreValue(ownValue))
{
continue;
}
const bool ownLower = (ownValue < iso_);
scalar nbrValue; scalar nbrValue;
point nbrPoint; point nbrPoint;
@ -384,7 +427,12 @@ void Foam::isoSurface::calcCutTypes
nbrPoint nbrPoint
); );
bool neiLower = (nbrValue < iso_); if (ignoreValue(nbrValue))
{
continue;
}
const bool neiLower = (nbrValue < iso_);
if (ownLower != neiLower) if (ownLower != neiLower)
{ {
@ -392,8 +440,8 @@ void Foam::isoSurface::calcCutTypes
} }
else else
{ {
// See if any mesh edge is cut by looping over all the edges of the // Is mesh edge cut?
// face. // - by looping over all the edges of the face.
const face f = mesh_.faces()[facei]; const face f = mesh_.faces()[facei];
if (isEdgeOfFaceCut(pVals, f, ownLower, neiLower)) if (isEdgeOfFaceCut(pVals, f, ownLower, neiLower))
@ -411,7 +459,8 @@ void Foam::isoSurface::calcCutTypes
forAll(pp, i) forAll(pp, i)
{ {
bool ownLower = (cVals[own[facei]] < iso_); const scalar& ownValue = cVals[own[facei]];
const bool ownLower = (ownValue < iso_);
scalar nbrValue; scalar nbrValue;
point nbrPoint; point nbrPoint;
@ -426,7 +475,7 @@ void Foam::isoSurface::calcCutTypes
nbrPoint nbrPoint
); );
bool neiLower = (nbrValue < iso_); const bool neiLower = (nbrValue < iso_);
if (ownLower != neiLower) if (ownLower != neiLower)
{ {
@ -434,7 +483,8 @@ void Foam::isoSurface::calcCutTypes
} }
else else
{ {
// Mesh edge. // Is mesh edge cut?
// - by looping over all the edges of the face.
const face f = mesh_.faces()[facei]; const face f = mesh_.faces()[facei];
if (isEdgeOfFaceCut(pVals, f, ownLower, neiLower)) if (isEdgeOfFaceCut(pVals, f, ownLower, neiLower))
@ -443,49 +493,73 @@ void Foam::isoSurface::calcCutTypes
} }
} }
facei++; ++facei;
} }
} }
nCutCells_ = 0; nCutCells_ = 0;
cellCutType_.setSize(mesh_.nCells()); cellCutType_.setSize(mesh_.nCells());
cellCutType_ = NOTCUT; cellCutType_ = NOTCUT;
for (label facei = 0; facei < mesh_.nInternalFaces(); facei++)
// Propagate internal face cuts into the cells.
// For cells marked as ignore (eg, GREAT) - skip this.
for (label facei = 0; facei < mesh_.nInternalFaces(); ++facei)
{ {
if (faceCutType_[facei] != NOTCUT) if (faceCutType_[facei] == NOTCUT)
{ {
if (cellCutType_[own[facei]] == NOTCUT) continue;
{ }
cellCutType_[own[facei]] = CUT;
nCutCells_++; if
} (
if (cellCutType_[nei[facei]] == NOTCUT) cellCutType_[own[facei]] == NOTCUT
{ && !ignoreValue(cVals[own[facei]])
cellCutType_[nei[facei]] = CUT; )
nCutCells_++; {
} cellCutType_[own[facei]] = CUT;
++nCutCells_;
}
if
(
cellCutType_[nei[facei]] == NOTCUT
&& !ignoreValue(cVals[nei[facei]])
)
{
cellCutType_[nei[facei]] = CUT;
++nCutCells_;
} }
} }
for (label facei = mesh_.nInternalFaces(); facei < mesh_.nFaces(); facei++)
// Propagate boundary face cuts into the cells.
// For cells marked as ignore (eg, GREAT) - skip this and
// also suppress the boundary face cut to prevent dangling face cuts.
for (label facei = mesh_.nInternalFaces(); facei < mesh_.nFaces(); ++facei)
{ {
if (faceCutType_[facei] != NOTCUT) if (faceCutType_[facei] == NOTCUT)
{ {
if (cellCutType_[own[facei]] == NOTCUT) continue;
{ }
cellCutType_[own[facei]] = CUT;
nCutCells_++; if (ignoreValue(cVals[own[facei]]))
} {
// Suppress dangling boundary face cut
faceCutType_[facei] = NOTCUT;
}
else if (cellCutType_[own[facei]] == NOTCUT)
{
cellCutType_[own[facei]] = CUT;
++nCutCells_;
} }
} }
if (debug) if (debug)
{ {
Pout<< "isoSurface : detected " << nCutCells_ Pout<< "isoSurface : candidate cut cells "
<< " candidate cut cells (out of " << mesh_.nCells() << nCutCells_ << " / " << mesh_.nCells() << endl;
<< ")." << endl;
} }
} }
@ -597,7 +671,7 @@ void Foam::isoSurface::calcSnappedCc
if (s[i] >= 0.0 && s[i] <= 0.5) if (s[i] >= 0.0 && s[i] <= 0.5)
{ {
otherPointSum += pt[i]; otherPointSum += pt[i];
nOther++; ++nOther;
} }
} }
} }
@ -792,7 +866,7 @@ void Foam::isoSurface::calcSnappedPoint
if (s[i] >= 0.0 && s[i] <= 0.5) if (s[i] >= 0.0 && s[i] <= 0.5)
{ {
otherPointSum += pt[i]; otherPointSum += pt[i];
nOther++; ++nOther;
} }
} }
} }
@ -1455,7 +1529,7 @@ Foam::isoSurface::isoSurface
forAll(pp, i) forAll(pp, i)
{ {
boundaryRegion[facei-mesh_.nInternalFaces()] = patchi; boundaryRegion[facei-mesh_.nInternalFaces()] = patchi;
facei++; ++facei;
} }
} }
@ -1464,6 +1538,38 @@ Foam::isoSurface::isoSurface
// Determine if any cut through face/cell // Determine if any cut through face/cell
calcCutTypes(boundaryRegion, meshC, cValsPtr_(), pVals_); calcCutTypes(boundaryRegion, meshC, cValsPtr_(), pVals_);
if (debug)
{
const fvMesh& fvm = mesh_;
volScalarField debugField
(
IOobject
(
"cutType",
fvm.time().timeName(),
fvm.time(),
IOobject::NO_READ,
IOobject::NO_WRITE,
false
),
fvm,
dimensionedScalar(dimless, Zero)
);
auto& debugFld = debugField.primitiveFieldRef();
forAll(cellCutType_, celli)
{
debugFld[celli] = cellCutType_[celli];
}
Pout<< "Writing cut types:"
<< debugField.objectPath() << endl;
debugField.write();
}
DynamicList<point> snappedPoints(nCutCells_); DynamicList<point> snappedPoints(nCutCells_);

View File

@ -3,7 +3,7 @@
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration | \\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation \\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\/ M anipulation | Copyright (C) 2016-2017 OpenCFD Ltd. \\/ M anipulation | Copyright (C) 2016-2018 OpenCFD Ltd.
------------------------------------------------------------------------------- -------------------------------------------------------------------------------
License License
This file is part of OpenFOAM. This file is part of OpenFOAM.
@ -54,7 +54,6 @@ Description
can use the neighbouring value. Any separated processor face or cyclic can use the neighbouring value. Any separated processor face or cyclic
face gets handled just like any boundary face. face gets handled just like any boundary face.
SourceFiles SourceFiles
isoSurface.C isoSurface.C
isoSurfaceTemplates.C isoSurfaceTemplates.C
@ -75,6 +74,8 @@ SourceFiles
namespace Foam namespace Foam
{ {
// Forward declarations
class fvMesh; class fvMesh;
class plane; class plane;
class treeBoundBox; class treeBoundBox;
@ -162,7 +163,7 @@ class isoSurface
bool noTransform(const tensor& tt) const; bool noTransform(const tensor& tt) const;
//- Is patch a collocated (i.e. non-separated) coupled patch? //- Is patch a collocated (i.e. non-separated) coupled patch?
static bool collocatedPatch(const polyPatch&); static bool collocatedPatch(const polyPatch& pp);
//- Per face whether is collocated //- Per face whether is collocated
bitSet collocatedFaces(const coupledPolyPatch&) const; bitSet collocatedFaces(const coupledPolyPatch&) const;
@ -291,7 +292,7 @@ class isoSurface
const bool hasSnap3, const bool hasSnap3,
const Type& snapP3, const Type& snapP3,
DynamicList<Type>& points DynamicList<Type>& pts
) const; ) const;
template<class Type> template<class Type>
@ -402,9 +403,9 @@ public:
// Constructors // Constructors
//- Construct from cell values and point values. Uses boundaryField //- Construct from cell values and point values.
// for boundary values. Holds reference to cellIsoVals and // Uses boundaryField for boundary values.
// pointIsoVals. // Holds reference to cellIsoVals and pointIsoVals.
isoSurface isoSurface
( (
const volScalarField& cellIsoVals, const volScalarField& cellIsoVals,
@ -418,14 +419,22 @@ public:
// Member Functions // Member Functions
//- For every face, the original cell in mesh //- For each face, the original cell in mesh
const labelList& meshCells() const const labelList& meshCells() const
{ {
return meshCells_; return meshCells_;
} }
//- Interpolates cCoords,pCoords. Uses the references to the original //- For each face, the original cell in mesh
// fields used to create the iso surface. labelList& meshCells()
{
return meshCells_;
}
//- Interpolates cCoords, pCoords.
// Uses the references to the original fields used to create the
// iso surface.
template<class Type> template<class Type>
tmp<Field<Type>> interpolate tmp<Field<Type>> interpolate
( (

View File

@ -44,6 +44,20 @@ namespace Foam
} }
// * * * * * * * * * * * * * * * Local Functions * * * * * * * * * * * * * * //
namespace Foam
{
// Avoid detecting change if the cells have been marked as GREAT
// (ie, ignore them)
static inline constexpr bool ignoreValue(const scalar val)
{
return (val >= 0.5*Foam::GREAT);
}
} // End namespace Foam
// * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * // // * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * //
Foam::scalar Foam::isoSurfaceCell::isoFraction Foam::scalar Foam::isoSurfaceCell::isoFraction
@ -52,16 +66,14 @@ Foam::scalar Foam::isoSurfaceCell::isoFraction
const scalar s1 const scalar s1
) const ) const
{ {
scalar d = s1-s0; const scalar d = s1-s0;
if (mag(d) > VSMALL) if (mag(d) > VSMALL)
{ {
return (iso_-s0)/d; return (iso_-s0)/d;
} }
else
{ return -1.0;
return -1.0;
}
} }
@ -71,9 +83,9 @@ bool Foam::isoSurfaceCell::isTriCut
const scalarField& pointValues const scalarField& pointValues
) const ) const
{ {
bool aLower = (pointValues[tri[0]] < iso_); const bool aLower = (pointValues[tri[0]] < iso_);
bool bLower = (pointValues[tri[1]] < iso_); const bool bLower = (pointValues[tri[1]] < iso_);
bool cLower = (pointValues[tri[2]] < iso_); const bool cLower = (pointValues[tri[2]] < iso_);
return !(aLower == bLower && aLower == cLower); return !(aLower == bLower && aLower == cLower);
} }
@ -87,15 +99,20 @@ Foam::isoSurfaceCell::cellCutType Foam::isoSurfaceCell::calcCutType
const label celli const label celli
) const ) const
{ {
if (ignoreValue(cellValues[celli]))
{
return NOTCUT;
}
const cell& cFaces = mesh_.cells()[celli]; const cell& cFaces = mesh_.cells()[celli];
if (isTet.test(celli)) if (isTet.test(celli))
{ {
forAll(cFaces, cFacei) for (const label facei : cFaces)
{ {
const face& f = mesh_.faces()[cFaces[cFacei]]; const face& f = mesh_.faces()[facei];
for (label fp = 1; fp < f.size() - 1; fp++) for (label fp = 1; fp < f.size() - 1; ++fp)
{ {
triFace tri(f[0], f[fp], f[f.fcIndex(fp)]); triFace tri(f[0], f[fp], f[f.fcIndex(fp)]);
@ -107,86 +124,90 @@ Foam::isoSurfaceCell::cellCutType Foam::isoSurfaceCell::calcCutType
} }
return NOTCUT; return NOTCUT;
} }
else
const bool cellLower = (cellValues[celli] < iso_);
// First check if there is any cut in cell
bool edgeCut = false;
for (const label facei : cFaces)
{ {
bool cellLower = (cellValues[celli] < iso_); const face& f = mesh_.faces()[facei];
// First check if there is any cut in cell // Check pyramids cut
bool edgeCut = false; for (const label labi : f)
forAll(cFaces, cFacei)
{ {
label facei = cFaces[cFacei]; if
const face& f = mesh_.faces()[facei]; (
!ignoreValue(pointValues[labi])
// Check pyramids cut && cellLower != (pointValues[labi] < iso_)
forAll(f, fp) )
{
if ((pointValues[f[fp]] < iso_) != cellLower)
{
edgeCut = true;
break;
}
}
if (edgeCut)
{
break;
}
const label fp0 = mesh_.tetBasePtIs()[facei];
label fp = f.fcIndex(fp0);
for (label i = 2; i < f.size(); i++)
{
label nextFp = f.fcIndex(fp);
if (isTriCut(triFace(f[fp0], f[fp], f[nextFp]), pointValues))
{
edgeCut = true;
break;
}
fp = nextFp;
}
if (edgeCut)
{ {
edgeCut = true;
break; break;
} }
} }
if (edgeCut) if (edgeCut)
{ {
// Count actual cuts (expensive since addressing needed) break;
// Note: not needed if you don't want to preserve maxima/minima
// centred around cellcentre. In that case just always return CUT
const labelList& cPoints = mesh_.cellPoints(celli);
label nPyrCuts = 0;
forAll(cPoints, i)
{
if ((pointValues[cPoints[i]] < iso_) != cellLower)
{
nPyrCuts++;
}
}
if (nPyrCuts == cPoints.size())
{
return SPHERE;
}
else
{
return CUT;
}
} }
else
const label fp0 = mesh_.tetBasePtIs()[facei];
label fp = f.fcIndex(fp0);
for (label i = 2; i < f.size(); i++)
{ {
return NOTCUT; const label nextFp = f.fcIndex(fp);
if (isTriCut(triFace(f[fp0], f[fp], f[nextFp]), pointValues))
{
edgeCut = true;
break;
}
fp = nextFp;
}
if (edgeCut)
{
break;
} }
} }
if (edgeCut)
{
// Count actual cuts (expensive since addressing needed)
// Note: not needed if you don't want to preserve maxima/minima
// centred around cellcentre. In that case just always return CUT
const labelList& cPoints = mesh_.cellPoints(celli);
label nCuts = 0;
for (const label pointi : cPoints)
{
if
(
!ignoreValue(pointValues[pointi])
&& cellLower != (pointValues[pointi] < iso_)
)
{
++nCuts;
}
}
if (nCuts == cPoints.size())
{
return SPHERE;
}
else if (nCuts > 1)
{
return CUT;
}
}
return NOTCUT;
} }
@ -205,14 +226,14 @@ void Foam::isoSurfaceCell::calcCutTypes
if (cellCutType_[celli] == CUT) if (cellCutType_[celli] == CUT)
{ {
nCutCells_++; ++nCutCells_;
} }
} }
if (debug) if (debug)
{ {
Pout<< "isoSurfaceCell : detected " << nCutCells_ Pout<< "isoSurfaceCell : candidate cut cells "
<< " candidate cut cells." << endl; << nCutCells_ << " / " << mesh_.nCells() << endl;
} }
} }
@ -383,7 +404,7 @@ void Foam::isoSurfaceCell::calcSnappedCc
{ {
if (cellCutType_[celli] == CUT && !isTet.test(celli)) if (cellCutType_[celli] == CUT && !isTet.test(celli))
{ {
scalar cVal = cVals[celli]; const scalar cVal = cVals[celli];
const cell& cFaces = mesh_.cells()[celli]; const cell& cFaces = mesh_.cells()[celli];
@ -394,14 +415,12 @@ void Foam::isoSurfaceCell::calcSnappedCc
// Create points for all intersections close to cell centre // Create points for all intersections close to cell centre
// (i.e. from pyramid edges) // (i.e. from pyramid edges)
forAll(cFaces, cFacei) for (const label facei : cFaces)
{ {
const face& f = mesh_.faces()[cFaces[cFacei]]; const face& f = mesh_.faces()[facei];
forAll(f, fp) for (const label pointi : f)
{ {
label pointi = f[fp];
scalar s = isoFraction(cVal, pVals[pointi]); scalar s = isoFraction(cVal, pVals[pointi]);
if (s >= 0.0 && s <= 0.5) if (s >= 0.0 && s <= 0.5)
@ -441,9 +460,8 @@ void Foam::isoSurfaceCell::calcSnappedCc
else if (localPoints.size()) else if (localPoints.size())
{ {
// Need to analyse // Need to analyse
forAll(cFaces, cFacei) for (const label facei : cFaces)
{ {
label facei = cFaces[cFacei];
const face& f = mesh_.faces()[facei]; const face& f = mesh_.faces()[facei];
// Do a tetrahedralisation. Each face to cc becomes pyr. // Do a tetrahedralisation. Each face to cc becomes pyr.
@ -622,13 +640,11 @@ void Foam::isoSurfaceCell::genPointTris
// Find 4th point // Find 4th point
label ccPointi = -1; label ccPointi = -1;
forAll(cFaces, cFacei) for (const label cfacei : cFaces)
{ {
const face& f1 = mesh_.faces()[cFaces[cFacei]]; const face& f1 = mesh_.faces()[cfacei];
forAll(f1, fp) for (const label p1 : f1)
{ {
label p1 = f1[fp];
if (!f.found(p1)) if (!f.found(p1))
{ {
ccPointi = p1; ccPointi = p1;
@ -697,10 +713,8 @@ void Foam::isoSurfaceCell::calcSnappedPoint
// snapped. Coupled boundaries are handled explicitly so not marked here. // snapped. Coupled boundaries are handled explicitly so not marked here.
bitSet isBoundaryPoint(mesh_.nPoints()); bitSet isBoundaryPoint(mesh_.nPoints());
const polyBoundaryMesh& patches = mesh_.boundaryMesh(); const polyBoundaryMesh& patches = mesh_.boundaryMesh();
forAll(patches, patchi) for (const polyPatch& pp : patches)
{ {
const polyPatch& pp = patches[patchi];
if (!pp.coupled()) if (!pp.coupled())
{ {
label facei = pp.start(); label facei = pp.start();
@ -708,10 +722,7 @@ void Foam::isoSurfaceCell::calcSnappedPoint
{ {
const face& f = mesh_.faces()[facei++]; const face& f = mesh_.faces()[facei++];
forAll(f, fp) isBoundaryPoint.setMany(f);
{
isBoundaryPoint.set(f[fp], 1);
}
} }
} }
} }
@ -728,7 +739,7 @@ void Foam::isoSurfaceCell::calcSnappedPoint
forAll(mesh_.pointFaces(), pointi) forAll(mesh_.pointFaces(), pointi)
{ {
if (isBoundaryPoint.get(pointi) == 1) if (isBoundaryPoint.test(pointi))
{ {
continue; continue;
} }
@ -737,10 +748,8 @@ void Foam::isoSurfaceCell::calcSnappedPoint
bool anyCut = false; bool anyCut = false;
forAll(pFaces, i) for (const label facei : pFaces)
{ {
label facei = pFaces[i];
if if
( (
cellCutType_[mesh_.faceOwner()[facei]] == CUT cellCutType_[mesh_.faceOwner()[facei]] == CUT
@ -766,10 +775,9 @@ void Foam::isoSurfaceCell::calcSnappedPoint
localPointCells.clear(); localPointCells.clear();
localTriPoints.clear(); localTriPoints.clear();
forAll(pFaces, pFacei) for (const label facei : pFaces)
{ {
label facei = pFaces[pFacei]; const label own = mesh_.faceOwner()[facei];
label own = mesh_.faceOwner()[facei];
if (isTet.test(own)) if (isTet.test(own))
{ {
@ -795,7 +803,7 @@ void Foam::isoSurfaceCell::calcSnappedPoint
if (mesh_.isInternalFace(facei)) if (mesh_.isInternalFace(facei))
{ {
label nei = mesh_.faceNeighbour()[facei]; const label nei = mesh_.faceNeighbour()[facei];
if (isTet.test(nei)) if (isTet.test(nei))
{ {
@ -1157,22 +1165,15 @@ bool Foam::isoSurfaceCell::danglingTriangle
) )
{ {
label nOpen = 0; label nOpen = 0;
forAll(fEdges, i) for (const label edgei : fEdges)
{ {
if (edgeFace1[fEdges[i]] == -1) if (edgeFace1[edgei] == -1)
{ {
nOpen++; ++nOpen;
} }
} }
if (nOpen == 1 || nOpen == 2 || nOpen == 3) return (nOpen == 1 || nOpen == 2 || nOpen == 3);
{
return true;
}
else
{
return false;
}
} }
@ -1191,32 +1192,31 @@ Foam::label Foam::isoSurfaceCell::markDanglingTriangles
label nDangling = 0; label nDangling = 0;
// Remove any dangling triangles // Remove any dangling triangles
forAllConstIter(Map<labelList>, edgeFacesRest, iter) forAllConstIters(edgeFacesRest, iter)
{ {
// These are all the non-manifold edges. Filter out all triangles // These are all the non-manifold edges. Filter out all triangles
// with only one connected edge (= this edge) // with only one connected edge (= this edge)
label edgeI = iter.key(); const label edgeI = iter.key();
const labelList& otherEdgeFaces = iter(); const labelList& otherEdgeFaces = iter.object();
// Remove all dangling triangles // Remove all dangling triangles
if (danglingTriangle(faceEdges[edgeFace0[edgeI]], edgeFace1)) if (danglingTriangle(faceEdges[edgeFace0[edgeI]], edgeFace1))
{ {
keepTriangles[edgeFace0[edgeI]] = false; keepTriangles[edgeFace0[edgeI]] = false;
nDangling++; ++nDangling;
} }
if (danglingTriangle(faceEdges[edgeFace1[edgeI]], edgeFace1)) if (danglingTriangle(faceEdges[edgeFace1[edgeI]], edgeFace1))
{ {
keepTriangles[edgeFace1[edgeI]] = false; keepTriangles[edgeFace1[edgeI]] = false;
nDangling++; ++nDangling;
} }
forAll(otherEdgeFaces, i) for (const label triI : otherEdgeFaces)
{ {
label triI = otherEdgeFaces[i];
if (danglingTriangle(faceEdges[triI], edgeFace1)) if (danglingTriangle(faceEdges[triI], edgeFace1))
{ {
keepTriangles[triI] = false; keepTriangles[triI] = false;
nDangling++; ++nDangling;
} }
} }
} }
@ -1250,10 +1250,8 @@ Foam::triSurface Foam::isoSurfaceCell::subsetMesh
// Renumber labels for face // Renumber labels for face
const triSurface::FaceType& f = s[oldFacei]; const triSurface::FaceType& f = s[oldFacei];
forAll(f, fp) for (const label oldPointi : f)
{ {
label oldPointi = f[fp];
if (oldToNewPoints[oldPointi] == -1) if (oldToNewPoints[oldPointi] == -1)
{ {
oldToNewPoints[oldPointi] = pointi; oldToNewPoints[oldPointi] = pointi;
@ -1313,9 +1311,19 @@ Foam::isoSurfaceCell::isoSurfaceCell
{ {
if (debug) if (debug)
{ {
Pout<< "isoSurfaceCell : mergeTol:" << mergeTol Pout<< "isoSurfaceCell::"
<< " mesh span:" << mesh.bounds().mag() << " cell min/max : "
<< " mergeDistance:" << mergeDistance_ << endl; << min(cVals_) << " / "
<< max(cVals_) << nl
<< " point min/max : "
<< min(pVals_) << " / "
<< max(pVals_) << nl
<< " isoValue : " << iso << nl
<< " regularise : " << regularise << nl
<< " mergeTol : " << mergeTol << nl
<< " mesh span : " << mesh.bounds().mag() << nl
<< " mergeDistance : " << mergeDistance_ << nl
<< endl;
} }
// Determine if cell is tet // Determine if cell is tet
@ -1336,6 +1344,39 @@ Foam::isoSurfaceCell::isoSurfaceCell
// Determine if any cut through cell // Determine if any cut through cell
calcCutTypes(isTet, cVals, pVals); calcCutTypes(isTet, cVals, pVals);
if (debug && isA<fvMesh>(mesh))
{
const fvMesh& fvm = dynamicCast<const fvMesh&>(mesh);
volScalarField debugField
(
IOobject
(
"cutType",
fvm.time().timeName(),
fvm.time(),
IOobject::NO_READ,
IOobject::NO_WRITE,
false
),
fvm,
dimensionedScalar(dimless, Zero)
);
auto& debugFld = debugField.primitiveFieldRef();
forAll(cellCutType_, celli)
{
debugFld[celli] = cellCutType_[celli];
}
Pout<< "Writing cut types:"
<< debugField.objectPath() << endl;
debugField.write();
}
DynamicList<point> snappedPoints(nCutCells_); DynamicList<point> snappedPoints(nCutCells_);
// Per cc -1 or a point inside snappedPoints. // Per cc -1 or a point inside snappedPoints.

View File

@ -57,6 +57,8 @@ SourceFiles
namespace Foam namespace Foam
{ {
// Forward declarations
class polyMesh; class polyMesh;
class triSurface; class triSurface;
@ -337,13 +339,20 @@ public:
// Member Functions // Member Functions
//- For every face, the original cell in mesh //- For each face, the original cell in mesh
const labelList& meshCells() const const labelList& meshCells() const
{ {
return meshCells_; return meshCells_;
} }
//- Interpolates cCoords,pCoords. //- For each face, the original cell in mesh
labelList& meshCells()
{
return meshCells_;
}
//- Interpolates cCoords, pCoords.
template<class Type> template<class Type>
tmp<Field<Type>> interpolate tmp<Field<Type>> interpolate
( (

View File

@ -44,11 +44,11 @@ Type Foam::isoSurfaceCell::generatePoint
const label p1Index const label p1Index
) const ) const
{ {
scalar d = s1-s0; const scalar d = s1-s0;
if (mag(d) > VSMALL) if (mag(d) > VSMALL)
{ {
scalar s = (iso_-s0)/d; const scalar s = (iso_-s0)/d;
if (s >= 0.5 && s <= 1 && p1Index != -1) if (s >= 0.5 && s <= 1 && p1Index != -1)
{ {
@ -124,22 +124,13 @@ void Foam::isoSurfaceCell::generateTriPoints
case 0x01: case 0x01:
case 0x0E: case 0x0E:
{ {
pts.append pts.append(generatePoint(snapped,s0,p0,p0Index,s1,p1,p1Index));
( pts.append(generatePoint(snapped,s0,p0,p0Index,s2,p2,p2Index));
generatePoint(snapped,s0,p0,p0Index,s1,p1,p1Index) pts.append(generatePoint(snapped,s0,p0,p0Index,s3,p3,p3Index));
);
pts.append
(
generatePoint(snapped,s0,p0,p0Index,s2,p2,p2Index)
);
pts.append
(
generatePoint(snapped,s0,p0,p0Index,s3,p3,p3Index)
);
if (triIndex == 0x0E) if (triIndex == 0x0E)
{ {
// Flip normals // Flip normals
label sz = pts.size(); const label sz = pts.size();
Swap(pts[sz-2], pts[sz-1]); Swap(pts[sz-2], pts[sz-1]);
} }
} }
@ -148,23 +139,14 @@ void Foam::isoSurfaceCell::generateTriPoints
case 0x02: case 0x02:
case 0x0D: case 0x0D:
{ {
pts.append pts.append(generatePoint(snapped,s1,p1,p1Index,s0,p0,p0Index));
( pts.append(generatePoint(snapped,s1,p1,p1Index,s3,p3,p3Index));
generatePoint(snapped,s1,p1,p1Index,s0,p0,p0Index) pts.append(generatePoint(snapped,s1,p1,p1Index,s2,p2,p2Index));
);
pts.append
(
generatePoint(snapped,s1,p1,p1Index,s3,p3,p3Index)
);
pts.append
(
generatePoint(snapped,s1,p1,p1Index,s2,p2,p2Index)
);
if (triIndex == 0x0D) if (triIndex == 0x0D)
{ {
// Flip normals // Flip normals
label sz = pts.size(); const label sz = pts.size();
Swap(pts[sz-2], pts[sz-1]); Swap(pts[sz-2], pts[sz-1]);
} }
} }
@ -173,15 +155,10 @@ void Foam::isoSurfaceCell::generateTriPoints
case 0x03: case 0x03:
case 0x0C: case 0x0C:
{ {
Type p0p2 = Type p0p2 = generatePoint(snapped,s0,p0,p0Index,s2,p2,p2Index);
generatePoint(snapped,s0,p0,p0Index,s2,p2,p2Index); Type p1p3 = generatePoint(snapped,s1,p1,p1Index,s3,p3,p3Index);
Type p1p3 =
generatePoint(snapped,s1,p1,p1Index,s3,p3,p3Index);
pts.append pts.append(generatePoint(snapped,s0,p0,p0Index,s3,p3,p3Index));
(
generatePoint(snapped,s0,p0,p0Index,s3,p3,p3Index)
);
pts.append(p1p3); pts.append(p1p3);
pts.append(p0p2); pts.append(p0p2);
@ -205,23 +182,14 @@ void Foam::isoSurfaceCell::generateTriPoints
case 0x04: case 0x04:
case 0x0B: case 0x0B:
{ {
pts.append pts.append(generatePoint(snapped,s2,p2,p2Index,s0,p0,p0Index));
( pts.append(generatePoint(snapped,s2,p2,p2Index,s1,p1,p1Index));
generatePoint(snapped,s2,p2,p2Index,s0,p0,p0Index) pts.append(generatePoint(snapped,s2,p2,p2Index,s3,p3,p3Index));
);
pts.append
(
generatePoint(snapped,s2,p2,p2Index,s1,p1,p1Index)
);
pts.append
(
generatePoint(snapped,s2,p2,p2Index,s3,p3,p3Index)
);
if (triIndex == 0x0B) if (triIndex == 0x0B)
{ {
// Flip normals // Flip normals
label sz = pts.size(); const label sz = pts.size();
Swap(pts[sz-2], pts[sz-1]); Swap(pts[sz-2], pts[sz-1]);
} }
} }
@ -230,29 +198,21 @@ void Foam::isoSurfaceCell::generateTriPoints
case 0x05: case 0x05:
case 0x0A: case 0x0A:
{ {
Type p0p1 = Type p0p1 = generatePoint(snapped,s0,p0,p0Index,s1,p1,p1Index);
generatePoint(snapped,s0,p0,p0Index,s1,p1,p1Index); Type p2p3 = generatePoint(snapped,s2,p2,p2Index,s3,p3,p3Index);
Type p2p3 =
generatePoint(snapped,s2,p2,p2Index,s3,p3,p3Index);
pts.append(p0p1); pts.append(p0p1);
pts.append(p2p3); pts.append(p2p3);
pts.append pts.append(generatePoint(snapped,s0,p0,p0Index,s3,p3,p3Index));
(
generatePoint(snapped,s0,p0,p0Index,s3,p3,p3Index)
);
pts.append(p0p1); pts.append(p0p1);
pts.append pts.append(generatePoint(snapped,s1,p1,p1Index,s2,p2,p2Index));
(
generatePoint(snapped,s1,p1,p1Index,s2,p2,p2Index)
);
pts.append(p2p3); pts.append(p2p3);
if (triIndex == 0x0A) if (triIndex == 0x0A)
{ {
// Flip normals // Flip normals
label sz = pts.size(); const label sz = pts.size();
Swap(pts[sz-5], pts[sz-4]); Swap(pts[sz-5], pts[sz-4]);
Swap(pts[sz-2], pts[sz-1]); Swap(pts[sz-2], pts[sz-1]);
} }
@ -262,29 +222,21 @@ void Foam::isoSurfaceCell::generateTriPoints
case 0x06: case 0x06:
case 0x09: case 0x09:
{ {
Type p0p1 = Type p0p1 = generatePoint(snapped,s0,p0,p0Index,s1,p1,p1Index);
generatePoint(snapped,s0,p0,p0Index,s1,p1,p1Index); Type p2p3 = generatePoint(snapped,s2,p2,p2Index,s3,p3,p3Index);
Type p2p3 =
generatePoint(snapped,s2,p2,p2Index,s3,p3,p3Index);
pts.append(p0p1); pts.append(p0p1);
pts.append pts.append(generatePoint(snapped,s1,p1,p1Index,s3,p3,p3Index));
(
generatePoint(snapped,s1,p1,p1Index,s3,p3,p3Index)
);
pts.append(p2p3); pts.append(p2p3);
pts.append(p0p1); pts.append(p0p1);
pts.append(p2p3); pts.append(p2p3);
pts.append pts.append(generatePoint(snapped,s0,p0,p0Index,s2,p2,p2Index));
(
generatePoint(snapped,s0,p0,p0Index,s2,p2,p2Index)
);
if (triIndex == 0x09) if (triIndex == 0x09)
{ {
// Flip normals // Flip normals
label sz = pts.size(); const label sz = pts.size();
Swap(pts[sz-5], pts[sz-4]); Swap(pts[sz-5], pts[sz-4]);
Swap(pts[sz-2], pts[sz-1]); Swap(pts[sz-2], pts[sz-1]);
} }
@ -294,22 +246,13 @@ void Foam::isoSurfaceCell::generateTriPoints
case 0x08: case 0x08:
case 0x07: case 0x07:
{ {
pts.append pts.append(generatePoint(snapped,s3,p3,p3Index,s0,p0,p0Index));
( pts.append(generatePoint(snapped,s3,p3,p3Index,s2,p2,p2Index));
generatePoint(snapped,s3,p3,p3Index,s0,p0,p0Index) pts.append(generatePoint(snapped,s3,p3,p3Index,s1,p1,p1Index));
);
pts.append
(
generatePoint(snapped,s3,p3,p3Index,s2,p2,p2Index)
);
pts.append
(
generatePoint(snapped,s3,p3,p3Index,s1,p1,p1Index)
);
if (triIndex == 0x07) if (triIndex == 0x07)
{ {
// Flip normals // Flip normals
label sz = pts.size(); const label sz = pts.size();
Swap(pts[sz-2], pts[sz-1]); Swap(pts[sz-2], pts[sz-1]);
} }
} }

View File

@ -3,7 +3,7 @@
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration | \\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation \\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\/ M anipulation | \\/ M anipulation | Copyright (C) 2018 OpenCFD Ltd.
------------------------------------------------------------------------------- -------------------------------------------------------------------------------
License License
This file is part of OpenFOAM. This file is part of OpenFOAM.
@ -53,31 +53,27 @@ Foam::isoSurface::adaptPatchFields
volMesh volMesh
> FieldType; > FieldType;
tmp<FieldType> tsliceFld auto tslice = tmp<FieldType>::New
( (
new FieldType IOobject
( (
IOobject fld.name(),
( fld.instance(),
fld.name(), fld.db(),
fld.instance(), IOobject::NO_READ,
fld.db(), IOobject::NO_WRITE,
IOobject::NO_READ, false
IOobject::NO_WRITE, ),
false fld, // internal field
), true // preserveCouples
fld, // internal field
true // preserveCouples
)
); );
FieldType& sliceFld = tsliceFld.ref(); auto& sliceFld = tslice.ref();
const fvMesh& mesh = fld.mesh(); const fvMesh& mesh = fld.mesh();
const polyBoundaryMesh& patches = mesh.boundaryMesh(); const polyBoundaryMesh& patches = mesh.boundaryMesh();
typename FieldType::Boundary& sliceFldBf = auto& sliceFldBf = sliceFld.boundaryFieldRef();
sliceFld.boundaryFieldRef();
forAll(patches, patchi) forAll(patches, patchi)
{ {
@ -146,7 +142,7 @@ Foam::isoSurface::adaptPatchFields
} }
} }
} }
return tsliceFld; return tslice;
} }
@ -164,11 +160,11 @@ Type Foam::isoSurface::generatePoint
const Type& snapP1 const Type& snapP1
) const ) const
{ {
scalar d = s1-s0; const scalar d = s1-s0;
if (mag(d) > VSMALL) if (mag(d) > VSMALL)
{ {
scalar s = (iso_-s0)/d; const scalar s = (iso_-s0)/d;
if (hasSnap1 && s >= 0.5 && s <= 1) if (hasSnap1 && s >= 0.5 && s <= 1)
{ {
@ -215,7 +211,7 @@ void Foam::isoSurface::generateTriPoints
const bool hasSnap3, const bool hasSnap3,
const Type& snapP3, const Type& snapP3,
DynamicList<Type>& points DynamicList<Type>& pts
) const ) const
{ {
// Note: cannot use simpler isoSurfaceCell::generateTriPoints since // Note: cannot use simpler isoSurfaceCell::generateTriPoints since
@ -248,185 +244,196 @@ void Foam::isoSurface::generateTriPoints
case 0x01: case 0x01:
case 0x0E: case 0x0E:
points.append {
pts.append
( (
generatePoint(s0,p0,hasSnap0,snapP0,s1,p1,hasSnap1,snapP1) generatePoint(s0,p0,hasSnap0,snapP0,s1,p1,hasSnap1,snapP1)
); );
points.append pts.append
( (
generatePoint(s0,p0,hasSnap0,snapP0,s2,p2,hasSnap2,snapP2) generatePoint(s0,p0,hasSnap0,snapP0,s2,p2,hasSnap2,snapP2)
); );
points.append pts.append
( (
generatePoint(s0,p0,hasSnap0,snapP0,s3,p3,hasSnap3,snapP3) generatePoint(s0,p0,hasSnap0,snapP0,s3,p3,hasSnap3,snapP3)
); );
if (triIndex == 0x0E) if (triIndex == 0x0E)
{ {
// Flip normals // Flip normals
label sz = points.size(); const label sz = pts.size();
Swap(points[sz-2], points[sz-1]); Swap(pts[sz-2], pts[sz-1]);
} }
}
break; break;
case 0x02: case 0x02:
case 0x0D: case 0x0D:
points.append {
pts.append
( (
generatePoint(s1,p1,hasSnap1,snapP1,s0,p0,hasSnap0,snapP0) generatePoint(s1,p1,hasSnap1,snapP1,s0,p0,hasSnap0,snapP0)
); );
points.append pts.append
( (
generatePoint(s1,p1,hasSnap1,snapP1,s3,p3,hasSnap3,snapP3) generatePoint(s1,p1,hasSnap1,snapP1,s3,p3,hasSnap3,snapP3)
); );
points.append pts.append
( (
generatePoint(s1,p1,hasSnap1,snapP1,s2,p2,hasSnap2,snapP2) generatePoint(s1,p1,hasSnap1,snapP1,s2,p2,hasSnap2,snapP2)
); );
if (triIndex == 0x0D) if (triIndex == 0x0D)
{ {
// Flip normals // Flip normals
label sz = points.size(); const label sz = pts.size();
Swap(points[sz-2], points[sz-1]); Swap(pts[sz-2], pts[sz-1]);
} }
}
break; break;
case 0x03: case 0x03:
case 0x0C: case 0x0C:
{ {
Type p0p2 = Type p0p2 =
generatePoint(s0,p0,hasSnap0,snapP0,s2,p2,hasSnap2,snapP2); generatePoint(s0,p0,hasSnap0,snapP0,s2,p2,hasSnap2,snapP2);
Type p1p3 = Type p1p3 =
generatePoint(s1,p1,hasSnap1,snapP1,s3,p3,hasSnap3,snapP3); generatePoint(s1,p1,hasSnap1,snapP1,s3,p3,hasSnap3,snapP3);
points.append pts.append
( (
generatePoint(s0,p0,hasSnap0,snapP0,s3,p3,hasSnap3,snapP3) generatePoint(s0,p0,hasSnap0,snapP0,s3,p3,hasSnap3,snapP3)
); );
points.append(p1p3); pts.append(p1p3);
points.append(p0p2); pts.append(p0p2);
pts.append(p1p3);
pts.append
(
generatePoint(s1,p1,hasSnap1,snapP1,s2,p2,hasSnap2,snapP2)
);
pts.append(p0p2);
points.append(p1p3);
points.append
(
generatePoint(s1,p1,hasSnap1,snapP1,s2,p2,hasSnap2,snapP2)
);
points.append(p0p2);
}
if (triIndex == 0x0C) if (triIndex == 0x0C)
{ {
// Flip normals // Flip normals
label sz = points.size(); const label sz = pts.size();
Swap(points[sz-5], points[sz-4]); Swap(pts[sz-5], pts[sz-4]);
Swap(points[sz-2], points[sz-1]); Swap(pts[sz-2], pts[sz-1]);
} }
}
break; break;
case 0x04: case 0x04:
case 0x0B: case 0x0B:
{ {
points.append pts.append
( (
generatePoint(s2,p2,hasSnap2,snapP2,s0,p0,hasSnap0,snapP0) generatePoint(s2,p2,hasSnap2,snapP2,s0,p0,hasSnap0,snapP0)
); );
points.append pts.append
( (
generatePoint(s2,p2,hasSnap2,snapP2,s1,p1,hasSnap1,snapP1) generatePoint(s2,p2,hasSnap2,snapP2,s1,p1,hasSnap1,snapP1)
); );
points.append pts.append
( (
generatePoint(s2,p2,hasSnap2,snapP2,s3,p3,hasSnap3,snapP3) generatePoint(s2,p2,hasSnap2,snapP2,s3,p3,hasSnap3,snapP3)
); );
}
if (triIndex == 0x0B) if (triIndex == 0x0B)
{ {
// Flip normals // Flip normals
label sz = points.size(); const label sz = pts.size();
Swap(points[sz-2], points[sz-1]); Swap(pts[sz-2], pts[sz-1]);
} }
}
break; break;
case 0x05: case 0x05:
case 0x0A: case 0x0A:
{ {
Type p0p1 = Type p0p1 =
generatePoint(s0,p0,hasSnap0,snapP0,s1,p1,hasSnap1,snapP1); generatePoint(s0,p0,hasSnap0,snapP0,s1,p1,hasSnap1,snapP1);
Type p2p3 = Type p2p3 =
generatePoint(s2,p2,hasSnap2,snapP2,s3,p3,hasSnap3,snapP3); generatePoint(s2,p2,hasSnap2,snapP2,s3,p3,hasSnap3,snapP3);
points.append(p0p1); pts.append(p0p1);
points.append(p2p3); pts.append(p2p3);
points.append pts.append
( (
generatePoint(s0,p0,hasSnap0,snapP0,s3,p3,hasSnap3,snapP3) generatePoint(s0,p0,hasSnap0,snapP0,s3,p3,hasSnap3,snapP3)
); );
pts.append(p0p1);
pts.append
(
generatePoint(s1,p1,hasSnap1,snapP1,s2,p2,hasSnap2,snapP2)
);
pts.append(p2p3);
points.append(p0p1);
points.append
(
generatePoint(s1,p1,hasSnap1,snapP1,s2,p2,hasSnap2,snapP2)
);
points.append(p2p3);
}
if (triIndex == 0x0A) if (triIndex == 0x0A)
{ {
// Flip normals // Flip normals
label sz = points.size(); const label sz = pts.size();
Swap(points[sz-5], points[sz-4]); Swap(pts[sz-5], pts[sz-4]);
Swap(points[sz-2], points[sz-1]); Swap(pts[sz-2], pts[sz-1]);
} }
}
break; break;
case 0x06: case 0x06:
case 0x09: case 0x09:
{ {
Type p0p1 = Type p0p1 =
generatePoint(s0,p0,hasSnap0,snapP0,s1,p1,hasSnap1,snapP1); generatePoint(s0,p0,hasSnap0,snapP0,s1,p1,hasSnap1,snapP1);
Type p2p3 = Type p2p3 =
generatePoint(s2,p2,hasSnap2,snapP2,s3,p3,hasSnap3,snapP3); generatePoint(s2,p2,hasSnap2,snapP2,s3,p3,hasSnap3,snapP3);
points.append(p0p1); pts.append(p0p1);
points.append pts.append
( (
generatePoint(s1,p1,hasSnap1,snapP1,s3,p3,hasSnap3,snapP3) generatePoint(s1,p1,hasSnap1,snapP1,s3,p3,hasSnap3,snapP3)
); );
points.append(p2p3); pts.append(p2p3);
pts.append(p0p1);
pts.append(p2p3);
pts.append
(
generatePoint(s0,p0,hasSnap0,snapP0,s2,p2,hasSnap2,snapP2)
);
points.append(p0p1);
points.append(p2p3);
points.append
(
generatePoint(s0,p0,hasSnap0,snapP0,s2,p2,hasSnap2,snapP2)
);
}
if (triIndex == 0x09) if (triIndex == 0x09)
{ {
// Flip normals // Flip normals
label sz = points.size(); label sz = pts.size();
Swap(points[sz-5], points[sz-4]); Swap(pts[sz-5], pts[sz-4]);
Swap(points[sz-2], points[sz-1]); Swap(pts[sz-2], pts[sz-1]);
} }
}
break; break;
case 0x08: case 0x08:
case 0x07: case 0x07:
points.append {
pts.append
( (
generatePoint(s3,p3,hasSnap3,snapP3,s0,p0,hasSnap0,snapP0) generatePoint(s3,p3,hasSnap3,snapP3,s0,p0,hasSnap0,snapP0)
); );
points.append pts.append
( (
generatePoint(s3,p3,hasSnap3,snapP3,s2,p2,hasSnap2,snapP2) generatePoint(s3,p3,hasSnap3,snapP3,s2,p2,hasSnap2,snapP2)
); );
points.append pts.append
( (
generatePoint(s3,p3,hasSnap3,snapP3,s1,p1,hasSnap1,snapP1) generatePoint(s3,p3,hasSnap3,snapP3,s1,p1,hasSnap1,snapP1)
); );
if (triIndex == 0x07) if (triIndex == 0x07)
{ {
// Flip normals // Flip normals
label sz = points.size(); label sz = pts.size();
Swap(points[sz-2], points[sz-1]); Swap(pts[sz-2], pts[sz-1]);
} }
}
break; break;
} }
} }
@ -565,7 +572,7 @@ void Foam::isoSurface::generateTriPoints
triPoints.clear(); triPoints.clear();
triMeshCells.clear(); triMeshCells.clear();
for (label facei = 0; facei < mesh_.nInternalFaces(); facei++) for (label facei = 0; facei < mesh_.nInternalFaces(); ++facei)
{ {
if (faceCutType_[facei] != NOTCUT) if (faceCutType_[facei] != NOTCUT)
{ {
@ -601,10 +608,8 @@ void Foam::isoSurface::generateTriPoints
// Determine neighbouring snap status // Determine neighbouring snap status
boolList neiSnapped(mesh_.nFaces()-mesh_.nInternalFaces(), false); boolList neiSnapped(mesh_.nFaces()-mesh_.nInternalFaces(), false);
List<Type> neiSnappedPoint(neiSnapped.size(), Type(Zero)); List<Type> neiSnappedPoint(neiSnapped.size(), Type(Zero));
forAll(patches, patchi) for (const polyPatch& pp : patches)
{ {
const polyPatch& pp = patches[patchi];
if (pp.coupled()) if (pp.coupled())
{ {
label facei = pp.start(); label facei = pp.start();
@ -626,7 +631,6 @@ void Foam::isoSurface::generateTriPoints
syncTools::swapBoundaryFaceList(mesh_, neiSnappedPoint); syncTools::swapBoundaryFaceList(mesh_, neiSnappedPoint);
forAll(patches, patchi) forAll(patches, patchi)
{ {
const polyPatch& pp = patches[patchi]; const polyPatch& pp = patches[patchi];
@ -748,8 +752,8 @@ Foam::isoSurface::interpolate
) )
{ {
// One value per point // One value per point
tmp<Field<Type>> tvalues(new Field<Type>(nPoints, Type(Zero))); auto tvalues = tmp<Field<Type>>::New(nPoints, Type(Zero));
Field<Type>& values = tvalues.ref(); auto& values = tvalues.ref();
// Pass1: unweighted average of merged point values // Pass1: unweighted average of merged point values

View File

@ -3,7 +3,7 @@
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration | \\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation \\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\/ M anipulation | \\/ M anipulation | Copyright (C) 2018 OpenCFD Ltd.
------------------------------------------------------------------------------- -------------------------------------------------------------------------------
License License
This file is part of OpenFOAM. This file is part of OpenFOAM.
@ -84,7 +84,6 @@ void Foam::thresholdCellFaces::calculate
label nFaces = 0; label nFaces = 0;
label nPoints = 0; label nPoints = 0;
meshCells_.clear(); meshCells_.clear();
DynamicList<face> surfFaces(0.5 * mesh_.nFaces()); DynamicList<face> surfFaces(0.5 * mesh_.nFaces());
@ -98,7 +97,7 @@ void Foam::thresholdCellFaces::calculate
{ {
int side = 0; int side = 0;
// check lowerThreshold // Check lowerThreshold
if (field[own[facei]] > lowerThreshold) if (field[own[facei]] > lowerThreshold)
{ {
if (field[nei[facei]] < lowerThreshold) if (field[nei[facei]] < lowerThreshold)
@ -111,7 +110,7 @@ void Foam::thresholdCellFaces::calculate
side = -1; side = -1;
} }
// check upperThreshold // Check upperThreshold
if (field[own[facei]] < upperThreshold) if (field[own[facei]] < upperThreshold)
{ {
if (field[nei[facei]] > upperThreshold) if (field[nei[facei]] > upperThreshold)
@ -129,11 +128,11 @@ void Foam::thresholdCellFaces::calculate
{ {
const face& f = origFaces[facei]; const face& f = origFaces[facei];
forAll(f, fp) for (const label pointi : f)
{ {
if (oldToNewPoints[f[fp]] == -1) if (oldToNewPoints[pointi] == -1)
{ {
oldToNewPoints[f[fp]] = nPoints++; oldToNewPoints[pointi] = nPoints++;
} }
} }
@ -201,11 +200,11 @@ void Foam::thresholdCellFaces::calculate
) )
{ {
const face& f = origFaces[facei]; const face& f = origFaces[facei];
forAll(f, fp) for (const label pointi : f)
{ {
if (oldToNewPoints[f[fp]] == -1) if (oldToNewPoints[pointi] == -1)
{ {
oldToNewPoints[f[fp]] = nPoints++; oldToNewPoints[pointi] = nPoints++;
} }
} }
@ -237,9 +236,9 @@ void Foam::thresholdCellFaces::calculate
surfCells.shrink(); surfCells.shrink();
// renumber // renumber
forAll(surfFaces, facei) for (face& f : surfFaces)
{ {
inplaceRenumber(oldToNewPoints, surfFaces[facei]); inplaceRenumber(oldToNewPoints, f);
} }
@ -250,7 +249,7 @@ void Foam::thresholdCellFaces::calculate
if (oldToNewPoints[pointi] >= 0) if (oldToNewPoints[pointi] >= 0)
{ {
surfPoints[oldToNewPoints[pointi]] = origPoints[pointi]; surfPoints[oldToNewPoints[pointi]] = origPoints[pointi];
nPoints++; ++nPoints;
} }
} }
surfPoints.setSize(nPoints); surfPoints.setSize(nPoints);
@ -276,7 +275,6 @@ Foam::thresholdCellFaces::thresholdCellFaces
: :
mesh_(mesh) mesh_(mesh)
{ {
if (lowerThreshold > upperThreshold) if (lowerThreshold > upperThreshold)
{ {
WarningInFunction WarningInFunction

View File

@ -3,7 +3,7 @@
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration | \\ / O peration |
\\ / A nd | Copyright (C) 2011 OpenFOAM Foundation \\ / A nd | Copyright (C) 2011 OpenFOAM Foundation
\\/ M anipulation | \\/ M anipulation | Copyright (C) 2018 OpenCFD Ltd.
------------------------------------------------------------------------------- -------------------------------------------------------------------------------
License License
This file is part of OpenFOAM. This file is part of OpenFOAM.
@ -59,14 +59,15 @@ class thresholdCellFaces
//- Reference to mesh //- Reference to mesh
const polyMesh& mesh_; const polyMesh& mesh_;
//- For every face the original cell in mesh //- For each face, the original cell in mesh
labelList meshCells_; labelList meshCells_;
// Private Member Functions // Private Member Functions
void calculate void calculate
( (
const scalarField&, const scalarField& field,
const scalar lowerThreshold, const scalar lowerThreshold,
const scalar upperThreshold, const scalar upperThreshold,
const bool triangulate const bool triangulate
@ -80,11 +81,11 @@ public:
// Constructors // Constructors
//- Construct from mesh, field and threshold value //- Construct from mesh, field and threshold values
thresholdCellFaces thresholdCellFaces
( (
const polyMesh&, const polyMesh& mesh,
const scalarField&, const scalarField& field,
const scalar lowerThreshold, const scalar lowerThreshold,
const scalar upperThreshold, const scalar upperThreshold,
const bool triangulate = false const bool triangulate = false
@ -93,14 +94,14 @@ public:
// Member Functions // Member Functions
//- For every face original cell in mesh //- For each face, the original cell in mesh
labelList& meshCells() const labelList& meshCells() const
{ {
return meshCells_; return meshCells_;
} }
//- For every face original cell in mesh //- For each face, the original cell in mesh
const labelList& meshCells() const labelList& meshCells()
{ {
return meshCells_; return meshCells_;
} }

View File

@ -81,9 +81,8 @@ void Foam::discreteSurface::setZoneMap
) )
{ {
label sz = 0; label sz = 0;
forAll(zoneLst, zonei) for (const surfZone& zn : zoneLst)
{ {
const surfZone& zn = zoneLst[zonei];
sz += zn.size(); sz += zn.size();
} }
@ -113,9 +112,8 @@ Foam::discreteSurface::nonCoupledboundaryTree() const
labelList bndFaces(mesh().nFaces()-mesh().nInternalFaces()); labelList bndFaces(mesh().nFaces()-mesh().nInternalFaces());
label bndI = 0; label bndI = 0;
forAll(patches, patchi) for (const polyPatch& pp : patches)
{ {
const polyPatch& pp = patches[patchi];
if (!pp.coupled()) if (!pp.coupled())
{ {
forAll(pp, i) forAll(pp, i)
@ -841,23 +839,24 @@ bool Foam::discreteSurface::update(const treeBoundBox& bb)
bool Foam::discreteSurface::sampleAndStore bool Foam::discreteSurface::sampleAndStore
( (
const objectRegistry& store, const objectRegistry& store,
const word& fieldName const word& fieldName,
const word& sampleScheme
) const ) const
{ {
return return
( (
sampleType<scalar>(store, fieldName) sampleType<scalar>(store, fieldName, sampleScheme)
|| sampleType<vector>(store, fieldName) || sampleType<vector>(store, fieldName, sampleScheme)
|| sampleType<sphericalTensor>(store, fieldName) || sampleType<sphericalTensor>(store, fieldName, sampleScheme)
|| sampleType<symmTensor>(store, fieldName) || sampleType<symmTensor>(store, fieldName, sampleScheme)
|| sampleType<tensor>(store, fieldName) || sampleType<tensor>(store, fieldName, sampleScheme)
); );
} }
void Foam::discreteSurface::print(Ostream& os) const void Foam::discreteSurface::print(Ostream& os) const
{ {
os << "discreteSurface: " os << "discreteSurface:"
<< " surface:" << surface_.objectRegistry::name() << " surface:" << surface_.objectRegistry::name()
<< " faces:" << this->surfFaces().size() << " faces:" << this->surfFaces().size()
<< " points:" << this->points().size() << " points:" << this->points().size()

View File

@ -3,7 +3,7 @@
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration | \\ / O peration |
\\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation \\ / A nd | Copyright (C) 2011-2016 OpenFOAM Foundation
\\/ M anipulation | Copyright (C) 2016 OpenCFD Ltd. \\/ M anipulation | Copyright (C) 2016-2018 OpenCFD Ltd.
------------------------------------------------------------------------------- -------------------------------------------------------------------------------
License License
This file is part of OpenFOAM. This file is part of OpenFOAM.
@ -155,13 +155,35 @@ private:
bool update(const meshSearch& meshSearcher); bool update(const meshSearch& meshSearcher);
protected:
// Protected Member Functions
//- Sample the volume field onto surface, //- Sample the volume field onto surface,
// store it (temporarily) onto the given registry // store it (temporarily) onto the given registry
template<class Type> template<class Type>
bool sampleType bool sampleType
( (
const objectRegistry& store, const objectRegistry& store,
const word& fieldName const word& fieldName,
const word& sampleScheme
) const;
//- Sample field on surface faces
template<class Type>
tmp<Field<Type>> sampleOnFaces
(
const interpolation<Type>& sampler
) const;
//- Sample field on surface points
template<class Type>
tmp<Field<Type>> sampleOnPoints
(
const interpolation<Type>& interpolator
) const; ) const;
@ -211,7 +233,7 @@ public:
static void setZoneMap(const surfZoneList&, labelList& zoneIds); static void setZoneMap(const surfZoneList&, labelList& zoneIds);
// Access // Access
//- Access to the underlying mesh //- Access to the underlying mesh
const polyMesh& mesh() const const polyMesh& mesh() const
@ -291,7 +313,8 @@ public:
virtual bool sampleAndStore virtual bool sampleAndStore
( (
const objectRegistry& store, const objectRegistry& store,
const word& fieldName const word& fieldName,
const word& sampleScheme
) const; ) const;
@ -299,28 +322,13 @@ public:
template<class Type> template<class Type>
tmp<Field<Type>> sampleType tmp<Field<Type>> sampleType
( (
const word& fieldName const word& fieldName,
) const; const word& sampleScheme
//- Sample field on surface
template<class Type>
tmp<Field<Type>> sampleField
(
const GeometricField<Type, fvPatchField, volMesh>&
) const;
//- Interpolate field on surface
template<class Type>
tmp<Field<Type>> interpolateField
(
const interpolation<Type>&
) const; ) const;
//- Write information //- Write information
virtual void print(Ostream&) const; virtual void print(Ostream& os) const;
}; };

View File

@ -2,7 +2,7 @@
========= | ========= |
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox \\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration | \\ / O peration |
\\ / A nd | Copyright (C) 2016 OpenCFD Ltd. \\ / A nd | Copyright (C) 2016-2018 OpenCFD Ltd.
\\/ M anipulation | \\/ M anipulation |
------------------------------------------------------------------------------- -------------------------------------------------------------------------------
License License
@ -32,20 +32,25 @@ template<class Type>
bool Foam::discreteSurface::sampleType bool Foam::discreteSurface::sampleType
( (
const objectRegistry& obr, const objectRegistry& obr,
const word& fieldName const word& fieldName,
const word& sampleScheme
) const ) const
{ {
typedef GeometricField<Type, fvPatchField, volMesh> VolFieldType; typedef GeometricField<Type, fvPatchField, volMesh> VolFieldType;
typedef DimensionedField<Type, surfGeoMesh> SurfFieldType; typedef DimensionedField<Type, surfGeoMesh> SurfFieldType;
typedef IOField<Type> TmpFieldType; typedef IOField<Type> TmpFieldType;
if (!mesh().foundObject<VolFieldType>(fieldName)) const auto* volFldPtr = mesh().lookupObjectPtr<VolFieldType>(fieldName);
if (!volFldPtr)
{ {
return false; return false;
} }
const VolFieldType& fld = mesh().lookupObject<VolFieldType>(fieldName); const auto& volFld = *volFldPtr;
tmp<Field<Type>> tfield = sampleField(fld); auto samplerPtr = interpolation<Type>::New(sampleScheme, *volFldPtr);
tmp<Field<Type>> tfield = sampleOnFaces(*samplerPtr);
// The rest could be moved into a separate helper // The rest could be moved into a separate helper
if (isA<surfMesh>(obr)) if (isA<surfMesh>(obr))
@ -67,7 +72,7 @@ bool Foam::discreteSurface::sampleType
IOobject::NO_WRITE IOobject::NO_WRITE
), ),
surf, surf,
dimensioned<Type>(fld.dimensions(), Zero) dimensioned<Type>(volFld.dimensions(), Zero)
); );
ptr->writeOpt() = IOobject::NO_WRITE; ptr->writeOpt() = IOobject::NO_WRITE;
@ -110,15 +115,18 @@ template<class Type>
Foam::tmp<Foam::Field<Type>> Foam::tmp<Foam::Field<Type>>
Foam::discreteSurface::sampleType Foam::discreteSurface::sampleType
( (
const word& fieldName const word& fieldName,
const word& sampleScheme
) const ) const
{ {
typedef GeometricField<Type, fvPatchField, volMesh> VolFieldType; typedef GeometricField<Type, fvPatchField, volMesh> VolFieldType;
if (mesh().foundObject<VolFieldType>(fieldName)) const auto* volFldPtr = mesh().lookupObjectPtr<VolFieldType>(fieldName);
if (volFldPtr)
{ {
const VolFieldType& fld = mesh().lookupObject<VolFieldType>(fieldName); auto samplerPtr = interpolation<Type>::New(sampleScheme, *volFldPtr);
return sampleField(fld); return sampleOnFaces(*samplerPtr);
} }
return nullptr; return nullptr;
@ -127,22 +135,33 @@ Foam::discreteSurface::sampleType
template<class Type> template<class Type>
Foam::tmp<Foam::Field<Type>> Foam::tmp<Foam::Field<Type>>
Foam::discreteSurface::sampleField Foam::discreteSurface::sampleOnFaces
( (
const GeometricField<Type, fvPatchField, volMesh>& vField const interpolation<Type>& sampler
) const ) const
{ {
const labelList& elements = sampleElements_;
const auto& vField = sampler.psi();
const label len = elements.size();
// One value per face // One value per face
tmp<Field<Type>> tvalues(new Field<Type>(sampleElements_.size())); auto tvalues = tmp<Field<Type>>::New(len);
Field<Type>& values = tvalues.ref(); auto& values = tvalues.ref();
if (!onBoundary()) if (!onBoundary())
{ {
// Sample cells // Sample cells
forAll(sampleElements_, triI) const faceList& fcs = this->surfFaces();
const pointField& pts = points();
for (label i=0; i < len; ++i)
{ {
values[triI] = vField[sampleElements_[triI]]; const label celli = elements[i];
const point pt = fcs[i].centre(pts);
values[i] = sampler.interpolate(pt, celli);
} }
} }
else else
@ -170,10 +189,10 @@ Foam::discreteSurface::sampleField
// Sample in flat boundary field // Sample in flat boundary field
forAll(sampleElements_, triI) for (label i=0; i < len; ++i)
{ {
label facei = sampleElements_[triI]; label facei = elements[i];
values[triI] = bVals[facei-mesh().nInternalFaces()]; values[i] = bVals[facei-mesh().nInternalFaces()];
} }
} }
@ -183,14 +202,14 @@ Foam::discreteSurface::sampleField
template<class Type> template<class Type>
Foam::tmp<Foam::Field<Type>> Foam::tmp<Foam::Field<Type>>
Foam::discreteSurface::interpolateField Foam::discreteSurface::sampleOnPoints
( (
const interpolation<Type>& interpolator const interpolation<Type>& interpolator
) const ) const
{ {
// One value per vertex // One value per vertex
tmp<Field<Type>> tvalues(new Field<Type>(sampleElements_.size())); auto tvalues = tmp<Field<Type>>::New(sampleElements_.size());
Field<Type>& values = tvalues.ref(); auto& values = tvalues.ref();
if (!onBoundary()) if (!onBoundary())
{ {

View File

@ -27,7 +27,7 @@ License
// * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * // // * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * //
Foam::MeshedSurfaceIOAllocator::MeshedSurfaceIOAllocator Foam::Detail::MeshedSurfaceIOAllocator::MeshedSurfaceIOAllocator
( (
const IOobject& ioPoints, const IOobject& ioPoints,
const IOobject& ioFaces, const IOobject& ioFaces,
@ -40,7 +40,7 @@ Foam::MeshedSurfaceIOAllocator::MeshedSurfaceIOAllocator
{} {}
Foam::MeshedSurfaceIOAllocator::MeshedSurfaceIOAllocator Foam::Detail::MeshedSurfaceIOAllocator::MeshedSurfaceIOAllocator
( (
const IOobject& ioPoints, const pointField& points, const IOobject& ioPoints, const pointField& points,
const IOobject& ioFaces, const faceList& faces, const IOobject& ioFaces, const faceList& faces,
@ -53,7 +53,7 @@ Foam::MeshedSurfaceIOAllocator::MeshedSurfaceIOAllocator
{} {}
Foam::MeshedSurfaceIOAllocator::MeshedSurfaceIOAllocator Foam::Detail::MeshedSurfaceIOAllocator::MeshedSurfaceIOAllocator
( (
const IOobject& ioPoints, pointField&& points, const IOobject& ioPoints, pointField&& points,
const IOobject& ioFaces, faceList&& faces, const IOobject& ioFaces, faceList&& faces,
@ -68,7 +68,7 @@ Foam::MeshedSurfaceIOAllocator::MeshedSurfaceIOAllocator
// * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * // // * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * //
Foam::MeshedSurfaceIOAllocator::~MeshedSurfaceIOAllocator() Foam::Detail::MeshedSurfaceIOAllocator::~MeshedSurfaceIOAllocator()
{ {
clear(); clear();
} }
@ -76,7 +76,10 @@ Foam::MeshedSurfaceIOAllocator::~MeshedSurfaceIOAllocator()
// * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * // // * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
void Foam::MeshedSurfaceIOAllocator::setInstance(const fileName& inst) void Foam::Detail::MeshedSurfaceIOAllocator::setInstance
(
const fileName& inst
)
{ {
points_.instance() = inst; points_.instance() = inst;
faces_.instance() = inst; faces_.instance() = inst;
@ -84,7 +87,10 @@ void Foam::MeshedSurfaceIOAllocator::setInstance(const fileName& inst)
} }
void Foam::MeshedSurfaceIOAllocator::setWriteOption(IOobject::writeOption wOpt) void Foam::Detail::MeshedSurfaceIOAllocator::setWriteOption
(
IOobject::writeOption wOpt
)
{ {
points_.writeOpt() = wOpt; points_.writeOpt() = wOpt;
faces_.writeOpt() = wOpt; faces_.writeOpt() = wOpt;
@ -92,7 +98,7 @@ void Foam::MeshedSurfaceIOAllocator::setWriteOption(IOobject::writeOption wOpt)
} }
void Foam::MeshedSurfaceIOAllocator::clear() void Foam::Detail::MeshedSurfaceIOAllocator::clear()
{ {
points_.clear(); points_.clear();
faces_.clear(); faces_.clear();
@ -100,7 +106,7 @@ void Foam::MeshedSurfaceIOAllocator::clear()
} }
bool Foam::MeshedSurfaceIOAllocator::writeObject bool Foam::Detail::MeshedSurfaceIOAllocator::writeObject
( (
IOstream::streamFormat fmt, IOstream::streamFormat fmt,
IOstream::versionNumber ver, IOstream::versionNumber ver,

View File

@ -22,7 +22,7 @@ License
along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>. along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>.
Class Class
Foam::MeshedSurfaceIOAllocator Foam::Detail::MeshedSurfaceIOAllocator
Description Description
A helper class for storing points, faces and zones with IO capabilities. A helper class for storing points, faces and zones with IO capabilities.
@ -43,9 +43,11 @@ SourceFiles
namespace Foam namespace Foam
{ {
namespace Detail
{
/*---------------------------------------------------------------------------*\ /*---------------------------------------------------------------------------*\
Class MeshedSurfaceIOAllocator Declaration Class Detail::MeshedSurfaceIOAllocator Declaration
\*---------------------------------------------------------------------------*/ \*---------------------------------------------------------------------------*/
class MeshedSurfaceIOAllocator class MeshedSurfaceIOAllocator
@ -64,10 +66,10 @@ class MeshedSurfaceIOAllocator
// Private Member Functions // Private Member Functions
//- Disallow copy construct //- No copy construct
MeshedSurfaceIOAllocator(const MeshedSurfaceIOAllocator&) = delete; MeshedSurfaceIOAllocator(const MeshedSurfaceIOAllocator&) = delete;
//- Disallow copy assignment //- No copy assignment
void operator=(const MeshedSurfaceIOAllocator&) = delete; void operator=(const MeshedSurfaceIOAllocator&) = delete;
@ -115,49 +117,49 @@ public:
void setWriteOption(IOobject::writeOption wOpt); void setWriteOption(IOobject::writeOption wOpt);
// Access // Access
//- Non-const access to the points //- Non-const access to the points
pointIOField& storedIOPoints() pointIOField& storedIOPoints()
{ {
return points_; return points_;
} }
//- Non-const access to the faces //- Non-const access to the faces
faceCompactIOList& storedIOFaces() faceCompactIOList& storedIOFaces()
{ {
return faces_; return faces_;
} }
//- Non-const access to the zones //- Non-const access to the zones
surfZoneIOList& storedIOZones() surfZoneIOList& storedIOZones()
{ {
return zones_; return zones_;
} }
//- Const access to the points //- Const access to the points
const pointIOField& storedIOPoints() const const pointIOField& storedIOPoints() const
{ {
return points_; return points_;
} }
//- Const access to the faces //- Const access to the faces
const faceCompactIOList& storedIOFaces() const const faceCompactIOList& storedIOFaces() const
{ {
return faces_; return faces_;
} }
//- Const access to the zones //- Const access to the zones
const surfZoneIOList& storedIOZones() const const surfZoneIOList& storedIOZones() const
{ {
return zones_; return zones_;
} }
// Storage Management // Storage Management
//- Clear primitive data (points, faces and zones) //- Clear primitive data (points, faces and zones)
void clear(); void clear();
// Writing // Writing
@ -176,6 +178,7 @@ public:
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
} // End namespace Detail
} // End namespace Foam } // End namespace Foam
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //

View File

@ -54,10 +54,10 @@ class ModifiableMeshedSurface
{ {
// Private Member Functions // Private Member Functions
//- Disallow copy construct //- No copy construct
ModifiableMeshedSurface(const ModifiableMeshedSurface<Face>&) = delete; ModifiableMeshedSurface(const ModifiableMeshedSurface<Face>&) = delete;
//- Disallow copy assignment //- No copy assignment
void operator=(const ModifiableMeshedSurface<Face>&) = delete; void operator=(const ModifiableMeshedSurface<Face>&) = delete;

View File

@ -57,7 +57,7 @@ template<class Face> class MeshedSurface;
class surfMesh class surfMesh
: :
public surfaceRegistry, public surfaceRegistry,
private MeshedSurfaceIOAllocator, private Detail::MeshedSurfaceIOAllocator,
public PrimitivePatch<face, ::Foam::UList, ::Foam::SubField<point>, point> public PrimitivePatch<face, ::Foam::UList, ::Foam::SubField<point>, point>
{ {
public: public:
@ -80,7 +80,7 @@ private:
// Private Typedefs // Private Typedefs
typedef MeshedSurfaceIOAllocator Allocator; typedef Detail::MeshedSurfaceIOAllocator Allocator;
typedef PrimitivePatch typedef PrimitivePatch
< <
@ -94,10 +94,10 @@ private:
// Private Member Functions // Private Member Functions
//- Disallow copy construct //- No copy construct
surfMesh(const surfMesh&) = delete; surfMesh(const surfMesh&) = delete;
//- Disallow copy assignment //- No copy assignment
void operator=(const surfMesh&) = delete; void operator=(const surfMesh&) = delete;

View File

@ -0,0 +1,11 @@
# An angled plane that extends beyond the geometry
o angledPlane
v -0.03 -0.08 -0.03
v -0.03 -0.08 0.03
v -0.07 -0.02 0.03
v -0.07 -0.02 -0.03
f 1 2 4
f 2 3 4
# EOF

View File

@ -45,7 +45,19 @@ fieldTransfer
${_plane} ${_plane}
bounds (-1 -1 -1) (0 0 1); bounds (-1 -1 -1) (0 0 1);
} }
// Angled plane - for general testing
plane3
{
type distanceSurface;
distance 0;
signed true;
surfaceType triSurfaceMesh;
surfaceName angledPlane.obj;
}
); );
} }
// ************************************************************************* // // ************************************************************************* //

View File

@ -54,6 +54,19 @@ UI2
} }
// Uniformity on sampled surface
UI3
{
${__surfaceFieldValue}
regionType surface;
name plane3;
operation uniformity;
fields ( U T );
}
// Inflow uniformity, but use a scalar field for weighting // Inflow uniformity, but use a scalar field for weighting
// Since this field is quite uniform, there should be no difference // Since this field is quite uniform, there should be no difference
T_UI1 T_UI1
@ -96,4 +109,5 @@ rhoU_UI2
fields ( p rho U rhoU ); fields ( p rho U rhoU );
} }
// ************************************************************************* // // ************************************************************************* //

View File

@ -0,0 +1,51 @@
// -*- C++ -*-
// ************************************************************************* //
debug
{
type surfaces;
libs ("libsampling.so");
log true;
writeControl timeStep;
writeInterval 1;
fields (rho U);
sampleScheme cellPoint;
interpolationScheme cellPoint;
surfaceFormat ensight;
formatOptions
{
ensight
{
collateTimes true;
}
}
surfaces
(
angledPlane
{
type distanceSurface;
distance 0;
signed true;
regularise true;
surfaceType triSurfaceMesh;
surfaceName angledPlane.obj;
}
iso
{
type isoSurface;
isoField p;
isoValue 1e5;
regularise true;
interpolate true;
}
);
}
// ************************************************************************* //

View File

@ -1,5 +1,5 @@
#-------------------------------*- makefile -*--------------------------------- #-------------------------------*- makefile -*---------------------------------
WM_VERSION = OPENFOAM=1804 WM_VERSION = OPENFOAM=1805
AR = ar AR = ar
ARFLAGS = cr ARFLAGS = cr