Commit 7ec17dfd authored by Henry's avatar Henry
Browse files

blockMesh: Add support for multi/sectional grading in a block

Consider a block describing a channel with two opposite walls.
Currently in order to grade the mesh towards the walls and have a
uniform region in the centre the channel would need to be spit into 3
blocks.  With the new multi/sectional grading this can be achieved in a
single block e.g.

blocks
(
    hex (0 1 2 3 4 5 6 7) (20 60 20)
    simpleGrading
    (
        1
        ((0.2 0.3 4) (0.6 0.4 1) (0.2 0.3 0.25))
        1
    )
);

In this example the block is divided uniformly in the x and z -directions
and split into three grading sections in the y-direction described by
three triples:  ((0.2 0.3 4) (0.6 0.4 1) (0.2 0.3 0.25)).  Each of the
grading sections is described by a triple consisting of the fraction of
the block, the fraction of the divisions and the grading ratio (size of
first division/size of last division).  Both the fraction of the block
and the fraction of the divisions are normalized automatically so they
can be specified scaled in anyway, e.g. as percentages:

blocks
(
    hex (0 1 2 3 4 5 6 7) (20 60 20)
    simpleGrading
    (
        1
        ((2 3 4) (6 4 1) (2 3 0.25))
        1
    )
);

and they need not sum to 1 or 100.

This is very new functionality and not well tested but backward
compatibility has been well tested so all existing blockMeshDicts should
parse correctly.
parent f6421f10
......@@ -10,6 +10,9 @@ curvedEdges/lineDivide.C
curvedEdges/BSplineEdge.C
curvedEdges/splineEdge.C
gradingDescriptor/gradingDescriptor.C
gradingDescriptor/gradingDescriptors.C
blockDescriptor/blockDescriptor.C
blockDescriptor/blockDescriptorEdges.C
......
......@@ -34,7 +34,7 @@ Foam::blockDescriptor::blockDescriptor
const pointField& blockPointField,
const curvedEdgeList& edges,
const Vector<label>& meshDensity,
const UList<scalar>& expand,
const UList<gradingDescriptors>& expand,
const word& zoneName
)
:
......@@ -77,7 +77,11 @@ Foam::blockDescriptor::blockDescriptor
meshDensity_(),
edgePoints_(12),
edgeWeights_(12),
expand_(12, 1.0),
expand_
(
12,
gradingDescriptors()
),
zoneName_()
{
// Examine next token
......@@ -126,7 +130,7 @@ Foam::blockDescriptor::blockDescriptor
is.putBack(t);
}
scalarList expRatios(is);
List<gradingDescriptors> expRatios(is);
if (expRatios.size() == 1)
{
......@@ -273,7 +277,7 @@ Foam::Ostream& Foam::operator<<(Ostream& os, const blockDescriptor& bd)
<< " simpleGrading (";
const scalarList& expand = bd.expand_;
const List<gradingDescriptors>& expand = bd.expand_;
// can we use a compact notation?
if
......
......@@ -41,6 +41,7 @@ SourceFiles
#include "pointField.H"
#include "scalarList.H"
#include "curvedEdgeList.H"
#include "gradingDescriptors.H"
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
......@@ -51,7 +52,6 @@ class Istream;
class Ostream;
// Forward declaration of friend functions and operators
class blockMesh;
class blockDescriptor;
Ostream& operator<<(Ostream&, const blockDescriptor&);
......@@ -82,11 +82,12 @@ class blockDescriptor
scalarListList edgeWeights_;
//- Expansion ratios in all directions
scalarList expand_;
List<gradingDescriptors> expand_;
//- Name of the zone (empty string if none)
word zoneName_;
// Private Member Functions
//- Set the points/weights for all edges
......@@ -113,7 +114,7 @@ public:
const pointField& blockPointField,
const curvedEdgeList&,
const Vector<label>& meshDensity,
const UList<scalar>& expand,
const UList<gradingDescriptors>& expand,
const word& zoneName = ""
);
......@@ -159,7 +160,6 @@ public:
//- Return the (optional) zone name
const word& zoneName() const;
//- Return the number of points
label nPoints() const;
......
......@@ -2,7 +2,7 @@
========= |
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration |
\\ / A nd | Copyright (C) 2011 OpenFOAM Foundation
\\ / A nd | Copyright (C) 2011-2015 OpenFOAM Foundation
\\/ M anipulation |
-------------------------------------------------------------------------------
License
......@@ -23,27 +23,10 @@ License
\*---------------------------------------------------------------------------*/
#include "error.H"
#include "blockDescriptor.H"
#include "lineEdge.H"
#include "lineDivide.H"
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
namespace Foam
{
//! \cond fileScope
// Calculate the geometric expension factor from the expansion ratio
inline scalar calcGexp(const scalar expRatio, const label dim)
{
return dim > 1 ? pow(expRatio, 1.0/(dim - 1)) : 0.0;
}
//! \endcond
} // End namespace Foam
// * * * * * * * * * * * * * Private Member Functions * * * * * * * * * * * //
void Foam::blockDescriptor::makeBlockEdges()
......@@ -52,21 +35,21 @@ void Foam::blockDescriptor::makeBlockEdges()
const label nj = meshDensity_.y();
const label nk = meshDensity_.z();
// these edges correspond to the "hex" cellModel
// These edges correspond to the "hex" cellModel
// x-direction
// X-direction
setEdge(0, 0, 1, ni);
setEdge(1, 3, 2, ni);
setEdge(2, 7, 6, ni);
setEdge(3, 4, 5, ni);
// y-direction
// Y-direction
setEdge(4, 0, 3, nj);
setEdge(5, 1, 2, nj);
setEdge(6, 5, 6, nj);
setEdge(7, 4, 7, nj);
// z-direction
// Z-direction
setEdge(8, 0, 4, nk);
setEdge(9, 1, 5, nk);
setEdge(10, 2, 6, nk);
......@@ -79,21 +62,18 @@ void Foam::blockDescriptor::setEdge
label edgeI,
label start,
label end,
label dim
label nDiv
)
{
// set reference to the list of labels defining the block
// Set reference to the list of labels defining the block
const labelList& blockLabels = blockShape_;
// set reference to global list of points
// Set reference to global list of points
const pointField blockPoints = blockShape_.points(blockPointField_);
// Set the edge points/weights
// The edge is a straight-line if it is not in the list of curvedEdges
// calc geometric expension factor from the expansion ratio
const scalar gExp = calcGexp(expand_[edgeI], dim);
forAll(curvedEdges_, cedgeI)
{
const curvedEdge& cedge = curvedEdges_[cedgeI];
......@@ -104,20 +84,20 @@ void Foam::blockDescriptor::setEdge
{
if (cmp > 0)
{
// curve has the same orientation
// Curve has the same orientation
// divide the line
lineDivide divEdge(cedge, dim, gExp);
// Divide the line
lineDivide divEdge(cedge, nDiv, expand_[edgeI]);
edgePoints_[edgeI] = divEdge.points();
edgeWeights_[edgeI] = divEdge.lambdaDivisions();
}
else
{
// curve has the opposite orientation
// Curve has the opposite orientation
// divide the line
lineDivide divEdge(cedge, dim, 1.0/(gExp+SMALL));
// Divide the line
lineDivide divEdge(cedge, nDiv, expand_[edgeI].inv());
const pointField& p = divEdge.points();
const scalarList& d = divEdge.lambdaDivisions();
......@@ -131,22 +111,20 @@ void Foam::blockDescriptor::setEdge
edgePoints_[edgeI][pI] = p[pMax - pI];
edgeWeights_[edgeI][pI] = 1.0 - d[pMax - pI];
}
}
// found curved-edge: done
// Found curved-edge: done
return;
}
}
// not found: divide the edge as a straight line
// Not curved-edge: divide the edge as a straight line
lineDivide divEdge
(
lineEdge(blockPoints, start, end),
dim,
gExp
nDiv,
expand_[edgeI]
);
edgePoints_[edgeI] = divEdge.points();
......
......@@ -2,7 +2,7 @@
========= |
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration |
\\ / A nd | Copyright (C) 2011 OpenFOAM Foundation
\\ / A nd | Copyright (C) 2011-2015 OpenFOAM Foundation
\\/ M anipulation |
-------------------------------------------------------------------------------
License
......@@ -23,45 +23,95 @@ License
\*---------------------------------------------------------------------------*/
#include "error.H"
#include "lineDivide.H"
#include "curvedEdge.H"
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
namespace Foam
{
//- Calculate the geometric expension factor from the expansion ratio
inline scalar calcGexp(const scalar expRatio, const label nDiv)
{
return nDiv > 1 ? pow(expRatio, 1.0/(nDiv - 1)) : 0.0;
}
}
// * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * //
Foam::lineDivide::lineDivide
(
const curvedEdge& cedge,
const label ndiv,
const scalar xratio
const label nDiv,
const gradingDescriptors& gd
)
:
points_(ndiv + 1),
divisions_(ndiv + 1)
points_(nDiv + 1),
divisions_(nDiv + 1)
{
divisions_[0] = 0.0;
divisions_[ndiv] = 1.0;
divisions_[nDiv] = 1.0;
// calculate the spacing
if (xratio == 1.0)
scalar secStart = divisions_[0];
label secnStart = 1;
// Check that there are more divisions than sections
if (nDiv >= gd.size())
{
for (label i=1; i < ndiv; i++)
forAll(gd, sectioni)
{
divisions_[i] = scalar(i)/ndiv;
scalar blockFrac = gd[sectioni].blockFraction();
scalar nDivFrac = gd[sectioni].nDivFraction();
scalar expRatio = gd[sectioni].expansionRatio();
label secnDiv = label(nDivFrac*nDiv + 0.5);
if (sectioni == gd.size() - 1)
{
secnDiv = nDiv - secnStart + 1;
}
label secnEnd = secnStart + secnDiv;
// Calculate the spacing
if (expRatio == 1.0)
{
for (label i = secnStart; i < secnEnd; i++)
{
divisions_[i] =
secStart
+ blockFrac*scalar(i - secnStart + 1)/secnDiv;
}
}
else
{
// Calculate geometric expansion factor from the expansion ratio
const scalar expFact = calcGexp(expRatio, secnDiv);
for (label i = secnStart; i < secnEnd; i++)
{
divisions_[i] =
secStart
+ blockFrac*(1.0 - pow(expFact, i - secnStart + 1))
/(1.0 - pow(expFact, secnDiv));
}
}
secStart = divisions_[secnEnd - 1];
secnStart = secnEnd;
}
}
// Otherwise mesh uniformly
else
{
for (label i=1; i < ndiv; i++)
for (label i=1; i < nDiv; i++)
{
divisions_[i] = (1.0 - pow(xratio, i))/(1.0 - pow(xratio, ndiv));
divisions_[i] = scalar(i)/nDiv;
}
}
// calculate the points
for (label i=0; i <= ndiv; i++)
// Calculate the points
for (label i = 0; i <= nDiv; i++)
{
points_[i] = cedge.position(divisions_[i]);
}
......
......@@ -2,7 +2,7 @@
========= |
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration |
\\ / A nd | Copyright (C) 2011 OpenFOAM Foundation
\\ / A nd | Copyright (C) 2011-2015 OpenFOAM Foundation
\\/ M anipulation |
-------------------------------------------------------------------------------
License
......@@ -37,6 +37,7 @@ SourceFiles
#include "pointField.H"
#include "scalarList.H"
#include "gradingDescriptors.H"
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
......@@ -61,12 +62,12 @@ public:
// Constructors
//- Construct from components with discretization and expansion ratio
//- Construct from components
lineDivide
(
const curvedEdge&,
const label ndiv,
const scalar xratio = 1.0
const gradingDescriptors& gd = gradingDescriptors()
);
......
/*---------------------------------------------------------------------------*\
========= |
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration |
\\ / A nd | Copyright (C) 2015 OpenFOAM Foundation
\\/ 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 "gradingDescriptor.H"
#include "IOstream.H"
#include "token.H"
// * * * * * * * * * * * * * * * * Constructors * * * * * * * * * * * * * * //
Foam::gradingDescriptor::gradingDescriptor()
:
blockFraction_(1),
nDivFraction_(1),
expansionRatio_(1)
{}
Foam::gradingDescriptor::gradingDescriptor
(
const scalar blockFraction,
const scalar nDivFraction,
const scalar expansionRatio
)
:
blockFraction_(blockFraction),
nDivFraction_(nDivFraction),
expansionRatio_(expansionRatio)
{}
Foam::gradingDescriptor::gradingDescriptor
(
const scalar expansionRatio
)
:
blockFraction_(1.0),
nDivFraction_(1.0),
expansionRatio_(expansionRatio)
{}
Foam::gradingDescriptor::gradingDescriptor(Istream& is)
{
is >> *this;
}
// * * * * * * * * * * * * * * * * Destructor * * * * * * * * * * * * * * * //
Foam::gradingDescriptor::~gradingDescriptor()
{}
// * * * * * * * * * * * * * * * Member Functions * * * * * * * * * * * * * //
Foam::gradingDescriptor Foam::gradingDescriptor::inv() const
{
return gradingDescriptor
(
blockFraction_,
nDivFraction_,
1.0/expansionRatio_
);
}
// * * * * * * * * * * * * * * * Member Operators * * * * * * * * * * * * * //
bool Foam::gradingDescriptor::operator==(const gradingDescriptor& gd) const
{
return
equal(blockFraction_, gd.blockFraction_)
&& equal(nDivFraction_, gd.nDivFraction_)
&& equal(expansionRatio_, gd.expansionRatio_);
}
bool Foam::gradingDescriptor::operator!=(const gradingDescriptor& gd) const
{
return !operator==(gd);
}
// * * * * * * * * * * * * * * * Friend Operators * * * * * * * * * * * * * //
Foam::Istream& Foam::operator>>(Istream& is, gradingDescriptor& gd)
{
// Examine next token
token t(is);
if (t.isNumber())
{
gd.blockFraction_ = 1.0;
gd.nDivFraction_ = 1.0;
gd.expansionRatio_ = t.number();
}
else if (t.isPunctuation() && t.pToken() == token::BEGIN_LIST)
{
is >> gd.blockFraction_ >> gd.nDivFraction_ >> gd.expansionRatio_;
is.readEnd("gradingDescriptor");
}
// Check state of Istream
is.check("operator>>(Istream&, gradingDescriptor&)");
return is;
}
Foam::Ostream& Foam::operator<<(Ostream& os, const gradingDescriptor& gd)
{
if (equal(gd.blockFraction_, 1.0))
{
os << gd.expansionRatio_;
}
else
{
os << token::BEGIN_LIST
<< gd.blockFraction_ << token::SPACE
<< gd.nDivFraction_ << token::SPACE
<< gd.expansionRatio_
<< token::END_LIST;
}
return os;
}
// ************************************************************************* //
/*---------------------------------------------------------------------------*\
========= |
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration |
\\ / A nd | Copyright (C) 2015 OpenFOAM Foundation
\\/ 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::gradingDescriptor
Description
Handles the specification for grading within a section of a block
blockFraction: the fraction of the block the section occupies
nDivFraction: the fraction of the divisions of the block allocated to
the section
expansionRatio: the expansions ratio for the grading with the section of
block defined as the ratio of the size of the division at either and
of the section.
SourceFiles
gradingDescriptor.C
\*---------------------------------------------------------------------------*/
#ifndef gradingDescriptor_H
#define gradingDescriptor_H
#include "scalar.H"
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
namespace Foam
{
class Istream;
class Ostream;
// Forward declaration of friend functions and operators
class gradingDescriptor;
class gradingDescriptors;
Istream& operator>>(Istream&, gradingDescriptor&);
Ostream& operator<<(Ostream&, const gradingDescriptor&);
/*---------------------------------------------------------------------------*\
Class gradingDescriptor Declaration
\*---------------------------------------------------------------------------*/
class gradingDescriptor
{
// Private data
scalar blockFraction_;
scalar nDivFraction_;
scalar expansionRatio_;