OpenFOAMにはいくつかのメッシュ作成・編集ツールが含まれます。 これらのツールを利用したメッシュ分割方法を紹介します。 ここでは、以下の図のような配管を例題とし、OpenFOAM-4.1を使います。
まず最初に作業用ディレクトリを作成します。
$ mkdir -p $FOAM_RUN/emsco-jp/mixingChamber/{0,constant,system}
$ cd $FOAM_RUN/emsco-jp/mixingChamber
合流部分のメッシュを作成します。
FoamFile
{
version 2.0;
format ascii;
class dictionary;
location "system";
object blockMeshDict;
}
convertToMeters 1.;
vertices
(
( -200. 0. -50.)
( -100. 0. -100.)
(-17.6777 0. -100.)
( 0. 0. -100.)
( -200. 0. -33.5355)
( -100. 0. -67.0711)
(-17.6777 0. -67.0711)
( 0. 0. -70.)
( -200. 0. -8.83883)
( -100. 0. -17.6777)
(-17.6777 0. -17.6777)
( 0. 0. -25.)
( -200. 0. 0.)
( -100. 0. 0.)
( -25. 0. 0.)
( -200. 27.5803 -27.9628)
( -100. 55.1606 -55.9255)
(-17.6777 55.1606 -55.9255)
( 0. 53.4276 -59.798)
( -200. 32.7797 -8.83883)
( -100. 65.5594 -17.6777)
(-17.6777 65.5594 -17.6777)
( 0. 64.4433 -25.)
( -200. 33.3333 0.)
( -100. 66.6667 0.)
( -25. 66.6667 0.)
( -200. 35.7299 -34.9768)
( -100. 71.4598 -69.9536)
(-17.6777 71.4598 -69.9536)
( 0. 68.3983 -72.9498)
( -200. 49.2125 -8.83883)
( -100. 98.4251 -17.6777)
(-17.6777 98.4251 -17.6777)
( 0. 96.8246 -25.)
( -200. 50. 0.)
( -100. 100. 0.)
( -25. 100. 0.)
( 0. 0. 0.)
( 0. 0. -15.)
(-12.5713 0. -12.5713)
( -15. 0. 0.)
( 0. 66.6667 0.)
( 0. 65.8703 -15.)
(-12.5713 66.1078 -12.5713)
( -15. 66.6667 0.)
( 0. 100. 0.)
( 0. 98.8686 -15.)
(-12.5713 99.2067 -12.5713)
( -15. 100. 0.)
( 0. 300. 0.)
( 0. 300. -15.)
(-12.5713 300. -12.5713)
( -15. 300. 0.)
( 0. 300. -25.)
(-17.6777 300. -17.6777)
( -25. 300. 0.)
);
blocks
(
hex ( 4 0 26 15 5 1 27 16) ( 4 8 16) simpleGrading ( 1 1 1)
hex ( 5 1 27 16 6 2 28 17) ( 4 8 10) simpleGrading ( 1 1 1)
hex ( 6 2 28 17 7 3 29 18) ( 4 8 3) simpleGrading ( 1 1 1)
hex ( 8 4 15 19 9 5 16 20) ( 6 8 16) simpleGrading ( 1 1 1)
hex ( 9 5 16 20 10 6 17 21) ( 6 8 10) simpleGrading ( 1 1 1)
hex ( 10 6 17 21 11 7 18 22) ( 6 8 3) simpleGrading ( 1 1 1)
hex ( 12 8 19 23 13 9 20 24) ( 3 8 16) simpleGrading ( 1 1 1)
hex ( 13 9 20 24 14 10 21 25) ( 3 8 10) simpleGrading ( 1 1 1)
hex ( 19 15 26 30 20 16 27 31) ( 6 4 16) simpleGrading ( 1 1 1)
hex ( 20 16 27 31 21 17 28 32) ( 6 4 10) simpleGrading ( 1 1 1)
hex ( 21 17 28 32 22 18 29 33) ( 6 4 3) simpleGrading ( 1 1 1)
hex ( 23 19 30 34 24 20 31 35) ( 3 4 16) simpleGrading ( 1 1 1)
hex ( 24 20 31 35 25 21 32 36) ( 3 4 10) simpleGrading ( 1 1 1)
hex ( 37 38 39 40 41 42 43 44) ( 3 3 8) simpleGrading ( 1 1 1)
hex ( 38 11 10 39 42 22 21 43) ( 2 3 8) simpleGrading ( 1 1 1)
hex ( 39 10 14 40 43 21 25 44) ( 2 3 8) simpleGrading ( 1 1 1)
hex ( 41 42 43 44 45 46 47 48) ( 3 3 4) simpleGrading ( 1 1 1)
hex ( 42 22 21 43 46 33 32 47) ( 2 3 4) simpleGrading ( 1 1 1)
hex ( 43 21 25 44 47 32 36 48) ( 2 3 4) simpleGrading ( 1 1 1)
hex ( 45 46 47 48 49 50 51 52) ( 3 3 24) simpleGrading ( 1 1 1)
hex ( 46 33 32 47 50 53 54 51) ( 2 3 24) simpleGrading ( 1 1 1)
hex ( 47 32 36 48 51 54 55 52) ( 2 3 24) simpleGrading ( 1 1 1)
);
edges
(
arc 0 26 ( -200. 19.3799 -46.0914)
arc 1 27 ( -100. 38.7598 -92.1828)
arc 2 28 (-17.6777 38.7599 -92.183)
arc 3 29 ( 0. 36.7765 -92.9919)
arc 4 15 ( -200. 14.0688 -32.1284)
arc 5 16 ( -100. 28.1377 -64.2568)
arc 6 17 (-17.6777 28.1377 -64.2568)
arc 7 18 ( 0. 27.1965 -67.4267)
arc 15 19 ( -200. 30.8521 -18.5835)
arc 16 20 ( -100. 61.7043 -37.1671)
arc 17 21 (-17.6777 61.7042 -37.1671)
arc 18 22 ( 0. 60.0609 -42.7552)
arc 19 23 ( -200. 33.1947 -4.42807)
arc 20 24 ( -100. 66.3896 -8.85616)
arc 26 30 ( -200. 44.4365 -22.9216)
arc 27 31 ( -100. 88.873 -45.8431)
arc 28 32 (-17.6777 88.873 -45.8431)
arc 29 33 ( 0. 86.0201 -50.9956)
arc 30 34 ( -200. 49.8027 -4.43692)
arc 31 35 ( -100. 99.6055 -8.87384)
arc 11 10 (-9.56709 0. -23.097)
arc 10 14 ( -23.097 0. -9.56709)
arc 38 39 (-6.40188 0. -14.3873)
arc 39 40 (-14.3873 0. -6.40188)
arc 41 42 ( 0. 66.4674 -7.51056)
arc 42 22 ( 0. 65.246 -20.0127)
arc 45 46 ( 0. 99.7167 -7.5213)
arc 46 33 ( 0. 97.9743 -20.0261)
arc 53 54 (-9.56709 300. -23.097)
arc 54 55 ( -23.097 300. -9.56709)
arc 50 51 (-6.40188 300. -14.3873)
arc 51 52 (-14.3873 300. -6.40188)
spline 6 7 ((-13.3898 0. -68.4441)
(-8.97586 0. -69.3334)
(-4.50057 0. -69.8366))
spline 17 18 ((-13.5157 54.3837 -57.6997)
( -9.115 53.8465 -58.89)
(-4.58527 53.5316 -59.574))
spline 28 29 ((-13.5188 70.0816 -71.3339)
(-9.11908 69.1344 -72.2527)
(-4.58804 68.5809 -72.7781))
spline 22 21 ((-4.88586 64.5289 -24.5179)
(-9.57849 64.7719 -23.0923)
(-13.8964 65.1341 -20.7819))
spline 21 25 ((-20.7819 65.9834 -13.8965)
(-23.0923 66.3425 -9.57842)
(-24.5179 66.5824 -4.88576))
spline 42 43 ((-3.21621 65.8866 -14.8464)
(-6.40285 65.9342 -14.3871)
(-9.53071 66.0098 -13.6263))
spline 43 44 ((-13.6252 66.3454 -9.5346)
(-14.3862 66.5217 -6.40754)
(-14.8461 66.6301 -3.21924))
spline 43 21 ((-13.8488 65.9881 -13.8488)
(-15.1257 65.8569 -15.1257)
( -16.402 65.7139 -16.402))
spline 33 32 ((-4.89486 96.9482 -24.5161)
(-9.59032 97.2984 -23.0873)
(-13.9039 97.8178 -20.777))
spline 32 36 ((-20.7769 99.0287 -13.9039)
(-23.0875 99.5391 -9.59004)
(-24.5162 99.8801 -4.89446))
spline 46 47 ((-3.21688 98.8918 -14.8463)
(-6.40384 98.9597 -14.3869)
(-9.53149 99.0673 -13.6261))
spline 47 48 ((-13.6238 99.544 -9.53933)
(-14.3851 99.7941 -6.41328)
(-14.8458 99.948 -3.22296))
spline 47 32 ((-13.8498 99.0363 -13.8498)
( -15.127 98.8492 -15.127)
(-16.4031 98.6455 -16.4031))
);
defaultPatch
{
name wall;
type wall;
}
boundary
(
inlet1
{
type patch;
faces
(
( 0 4 15 26)
( 4 8 19 15)
( 15 19 30 26)
( 8 12 23 19)
( 19 23 34 30)
);
}
inlet2
{
type patch;
faces
(
( 49 50 51 52)
( 50 53 54 51)
( 51 54 55 52)
);
}
outlet
{
type patch;
faces
(
);
}
xsymm
{
type symmetryPlane;
faces
(
( 3 29 18 7)
( 7 18 22 11)
( 18 29 33 22)
( 37 38 42 41)
( 38 11 22 42)
( 41 42 46 45)
( 42 22 33 46)
( 45 46 50 49)
( 46 33 53 50)
);
}
ysymm
{
type symmetryPlane;
faces
(
( 0 1 5 4)
( 1 2 6 5)
( 2 3 7 6)
( 4 5 9 8)
( 5 6 10 9)
( 6 7 11 10)
( 8 9 13 12)
( 9 10 14 13)
( 37 40 39 38)
( 38 39 10 11)
( 39 40 14 10)
);
}
zsymm
{
type symmetryPlane;
faces
(
( 12 13 24 23)
( 13 14 25 24)
( 23 24 35 34)
( 24 25 36 35)
( 40 37 41 44)
( 14 40 44 25)
( 44 41 45 48)
( 25 44 48 36)
( 48 45 49 52)
( 36 48 52 55)
);
}
);
mergePatchPairs
(
);
FoamFile
{
version 2.0;
format ascii;
class dictionary;
location "system";
object controlDict;
}
deltaT 1;
writeInterval 1;
$ blockMesh > log.blockMesh

x=0の平面で鏡面コピーします。
FoamFile
{
version 2.0;
format ascii;
class dictionary;
location "system";
object mirrorMeshDict;
}
planeType pointAndNormal;
pointAndNormalDict
{
basePoint (0 0 0);
normalVector (1 0 0);
}
planeTolerance 1.e-3;
$ cp system/mirrorMeshDict.1 system/mirrorMeshDict $ mirrorMesh -overwrite > log.mirrorMesh.1

同様に、y=0の平面とz=0の平面で鏡面コピーします。
FoamFile
{
version 2.0;
format ascii;
class dictionary;
location "system";
object mirrorMeshDict;
}
planeType pointAndNormal;
pointAndNormalDict
{
basePoint (0 0 0);
normalVector (0 1 0);
}
planeTolerance 1.e-3;
FoamFile
{
version 2.0;
format ascii;
class dictionary;
location "system";
object mirrorMeshDict;
}
planeType pointAndNormal;
pointAndNormalDict
{
basePoint (0 0 0);
normalVector (0 0 1);
}
planeTolerance 1.e-3;
$ cp system/mirrorMeshDict.2 system/mirrorMeshDict $ mirrorMesh -overwrite > log.mirrorMesh.2 $ cp system/mirrorMeshDict.3 system/mirrorMeshDict $ mirrorMesh -overwrite > log.mirrorMesh.3

x=0の平面で鏡面コピーしたときに、太いパイプの入り口条件(inlet1)が本来は出口である反対にも設定されています。 パッチを2つに分割して、出口側のパッチをoutletに修正します。
FoamFile
{
version 2.0;
format ascii;
class dictionary;
location "system";
object topoSetDict;
}
actions
(
{
name f0;
type faceSet;
action new;
source patchToFace;
sourceInfo
{
name "inlet1";
}
}
{
name f0;
type faceSet;
action delete;
source normalToFace;
sourceInfo
{
normal (1 0 0);
cos 0.01;
}
}
{
name f1;
type faceSet;
action new;
source patchToFace;
sourceInfo
{
name "inlet1";
}
}
{
name f1;
type faceSet;
action delete;
source normalToFace;
sourceInfo
{
normal (-1 0 0);
cos 0.01;
}
}
);
FoamFile
{
version 2.0;
format ascii;
class dictionary;
location "system";
object createPatchDict;
}
pointSync false;
patches
(
{
name "inlet1";
patchInfo
{
type patch;
}
constructFrom set;
set f0;
}
{
name "outlet";
patchInfo
{
type patch;
}
constructFrom set;
set f1;
}
);
$ topoSet -dict system/topoSetDict.1 > log.topoSet.1 $ createPatch -overwrite > log.createPatch


y=0の平面で鏡面コピーしたときに細いパイプが上下の2つできています。必要な領域だけを残して、余分な領域を削除します。
FoamFile
{
version 2.0;
format ascii;
class dictionary;
location "system";
object topoSetDict;
}
actions
(
{
name c0;
type cellSet;
action new;
source cylinderToCell;
sourceInfo
{
p1 ( 200.001 0. 0.);
p2 (-200.001 0. 0.);
radius 100.001;
}
}
{
name c0;
type cellSet;
action add;
source cylinderToCell;
sourceInfo
{
p1 (0. 0. 0.);
p2 (0. 300.001 0.);
radius 50.001;
}
}
);
FoamFile
{
version 2.0;
format ascii;
class dictionary;
location "system";
object fvSchemes;
}
gradSchemes
{
}
divSchemes
{
}
laplacianSchemes
{
}
FoamFile
{
version 2.0;
format ascii;
class dictionary;
location "system";
object fvSolution;
}
// このファイルはヘッダ情報のみ
$ topoSet -dict system/topoSetDict.2 > log.topoSet.2 $ subsetMesh c0 -patch wall -overwrite > log.subsetMesh

入り口側を300mmだけ−x方向に押し出します。
FoamFile
{
version 2.0;
format ascii;
class dictionary;
location "system";
object extrudeMeshDict;
}
constructFrom mesh;
sourceCase "$FOAM_CASE";
sourcePatches
(
inlet1
);
exposedPatchName inlet1;
flipNormals false;
extrudeModel linearDirection;
nLayers 40;
expansionRatio 1;
linearDirectionCoeffs
{
direction (-1 0 0);
thickness 300;
}
mergeFaces false;
$ cp system/extrudeMeshDict.1 system/extrudeMeshDict $ extrudeMesh > log.extrudeMesh.1

同様に、出口側を300mmだけ+x方向に押し出します。
FoamFile
{
version 2.0;
format ascii;
class dictionary;
location "system";
object extrudeMeshDict;
}
constructFrom mesh;
sourceCase "$FOAM_CASE";
sourcePatches
(
outlet
);
exposedPatchName outlet;
flipNormals false;
extrudeModel linearDirection;
nLayers 40;
expansionRatio 1;
linearDirectionCoeffs
{
direction (1 0 0);
thickness 300;
}
mergeFaces false;
$ cp system/extrudeMeshDict.2 system/extrudeMeshDict $ extrudeMesh > log.extrudeMesh.2

出口側を90degだけ回転させながら、押し出します。
FoamFile
{
version 2.0;
format ascii;
class dictionary;
location "system";
object extrudeMeshDict;
}
constructFrom mesh;
sourceCase "$FOAM_CASE";
sourcePatches
(
outlet
);
exposedPatchName outlet;
flipNormals false;
extrudeModel sector;
nLayers 40;
expansionRatio 1;
sectorCoeffs
{
axisPt (500 -200 0.);
axis (0 0 -1);
angle 90;
}
mergeFaces false;
$ cp system/extrudeMeshDict.3 system/extrudeMeshDict $ extrudeMesh > log.extrudeMesh.3

出口側を300mmだけ−y方向に押し出します。
FoamFile
{
version 2.0;
format ascii;
class dictionary;
location "system";
object extrudeMeshDict;
}
constructFrom mesh;
sourceCase "$FOAM_CASE";
sourcePatches
(
"outlet"
);
exposedPatchName outlet;
flipNormals false;
extrudeModel linearDirection;
nLayers 40;
expansionRatio 1;
linearDirectionCoeffs
{
direction (0 -1 0);
thickness 300;
}
mergeFaces false;
$ cp system/extrudeMeshDict.4 system/extrudeMeshDict $ extrudeMesh > log.extrudeMesh.4

ここまで長さの単位としてミリメートルを使ってきましたが、OpenFOAMではメートル単位を使います。長さの単位を変更するために1000分の1倍にスケールします。
$ transformPoints -scale '(0.001 0.001 0.001)' > log.transformPoints
メッシュ品質をチェックします。メッシュ品質に問題がなければ、メッシュの完成です。
$ checkMesh
/*---------------------------------------------------------------------------*\
| ========= | |
| \\ / F ield | OpenFOAM: The Open Source CFD Toolbox |
| \\ / O peration | Version: 4.1 |
| \\ / A nd | Web: www.OpenFOAM.org |
| \\/ M anipulation | |
\*---------------------------------------------------------------------------*/
Build : 4.1
Exec : checkMesh
Date : Mar 09 2017
Time : 19:14:28
Host : "?????"
PID : 16049
Case : /home/?????/OpenFOAM/?????-4.1/run/emsco-jp/mixingChamber
nProcs : 1
sigFpe : Enabling floating point exception trapping (FOAM_SIGFPE).
fileModificationChecking : Monitoring run-time modified files using timeStampMaster
allowSystemOperations : Allowing user-supplied system call operations
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
Create time
Create polyMesh for time = 0
Time = 0
Mesh stats
points: 133833
faces: 384052
internal faces: 367436
cells: 125248
faces per cell: 6
boundary patches: 4
point zones: 0
face zones: 0
cell zones: 0
Overall number of cells of each type:
hexahedra: 125248
prisms: 0
wedges: 0
pyramids: 0
tet wedges: 0
tetrahedra: 0
polyhedra: 0
Checking topology...
Boundary definition OK.
Cell to face addressing OK.
Point usage OK.
Upper triangular ordering OK.
Face vertices OK.
Number of regions: 1 (OK).
Checking patch topology for multiply connected surfaces...
Patch Faces Points Surface topology
inlet1 560 595 ok (non-closed singly connected)
inlet2 84 97 ok (non-closed singly connected)
wall 15412 15491 ok (non-closed singly connected)
outlet 560 595 ok (non-closed singly connected)
Checking geometry...
Overall domain bounding box (-0.5 -0.5 -0.1) (0.75 0.3 0.1)
Mesh has 3 geometric (non-empty/wedge) directions (1 1 1)
Mesh has 3 solution (non-empty) directions (1 1 1)
Boundary openness (-1.6261e-16 9.69057e-17 7.57401e-16) OK.
Max cell openness = 2.68995e-16 OK.
Max aspect ratio = 4.55121 OK.
Minimum face area = 9.44458e-06. Maximum face area = 8.18832e-05. Face area magnitudes OK.
Min volume = 6.28078e-08. Max volume = 6.47251e-07. Total volume = 0.019845. Cell volumes OK.
Mesh non-orthogonality Max: 41.0009 average: 9.71381
Non-orthogonality check OK.
Face pyramids OK.
Max skewness = 0.530471 OK.
Coupled point location match (average 0) OK.
Mesh OK.
End
最後に、ここまでの手順を自動化します。
#!/bin/sh
cd ${0%/*} || exit 1
blockMesh > log.blockMesh
for i in 1 2 3
do
cp system/mirrorMeshDict.$i system/mirrorMeshDict
mirrorMesh -overwrite > log.mirrorMesh.$i
done
topoSet -dict system/topoSetDict.1 > log.topoSet.1
createPatch -overwrite > log.createPatch
topoSet -dict system/topoSetDict.2 > log.topoSet.2
subsetMesh c0 -patch wall -overwrite > log.subsetMesh
for i in 1 2 3 4
do
cp system/extrudeMeshDict.$i system/extrudeMeshDict
extrudeMesh > log.extrudeMesh.$i
done
transformPoints -scale '(0.001 0.001 0.001)' > log.transformPoints
$ chmod 755 Allrun $ ./Allrun