简介
OpenFoam的首选网格生成器是blockMesh。blockMesh可以根据blockMeshDict这个字典中的信息生成openFoam网格。但是有时候需要修改网格,而网格中的几何点之间又存在约束关系,如果手动修改blockMeshDict那么工作量将是巨大的,所以有必要使用javaScript脚本直接生成blockMeshDict文件
代码与解释
在OpenFoam案例的system文件夹中新建一个空白文件,名称为meshGenerator.js
。我们将编写一个javaScript脚本来生成blockMeshDict文件。
若生成一个简易固体火箭发动机的网格,代码如下:
//定义数据字典字典的头
var blockMeshDict =
`/*--------------------------------*- C++ -*----------------------------------*\\
========= |
\\\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\\\ / O peration | Website: https://openfoam.org
\\\\ / A nd | Version: 8
\\\\/ M anipulation |
\\*---------------------------------------------------------------------------*/
FoamFile
{
version 2.0;
format ascii;
class dictionary;
object blockMeshDict;
}
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
convertToMeters 0.0254;
`
//注意:楔形角度为2度
const tanTheta = Math.tan(Math.PI / 180.0)
//网格细化倍数
const finer = 1.0;
//注意:长度单位都是inch,1 inch = 2.54 cm = 0.0254 m
const R = 6, RT = 1, L = 20, dL = 1//发动机内半径,喉部半径,装药长度,装药与前封头之间的间隙
const RA = RB = 2.0 * RT//过渡圆弧的半径,分别是收敛段和扩张段的
const alpha = 45.0 * Math.PI / 180.0, beta = 15.0 * Math.PI / 180.0//收敛段和扩张段的半角(弧度制)
const epson = 9.5//喷管的扩张比
const y1 = RA * (1 - Math.cos(alpha)) + RT
const x1 = (R - y1)/ Math.tan(alpha)
const y2 = RT
const x2 = RA * Math.sin(alpha)
const y3 = RB * (1 - Math.cos(beta)) + RT
const x3 = RB * Math.sin(beta)
const y4 = Math.sqrt(epson) * RT
const x4 = (y4 - y3) / Math.tan(beta)
//定义vertices字段
var vertices = []
vertices.push({ x: -dL, y: 0, z: 0 })
vertices.push({ x: -dL, y: R, z: -R * tanTheta })
vertices.push({ x: -dL, y: R, z: R * tanTheta })
vertices.push({ x: L, y: 0, z: 0 })
vertices.push({ x: L, y: R, z: -R * tanTheta })
vertices.push({ x: L, y: R, z: R * tanTheta })
vertices.push({ x: L + x1, y: 0, z: 0 })
vertices.push({ x: L + x1, y: y1, z: -y1 * tanTheta })
vertices.push({ x: L + x1, y: y1, z: y1 * tanTheta })
vertices.push({ x: L + x1 + x2 + x3, y: 0, z: 0 })
vertices.push({ x: L + x1 + x2 + x3, y: y3, z: -y3 * tanTheta })
vertices.push({ x: L + x1 + x2 + x3, y: y3, z: y3 * tanTheta })
vertices.push({ x: L + x1 + x2 + x3 + x4, y: 0, z: 0 })
vertices.push({ x: L + x1 + x2 + x3 + x4, y: y4, z: -y4 * tanTheta })
vertices.push({ x: L + x1 + x2 + x3 + x4, y: y4, z: y4 * tanTheta })
blockMeshDict += verticesToString(vertices)
//定义blocks字段
var blocks = []
blocks.push({ type: "hex", topology: [0, 3, 4, 1, 0, 3, 5, 2], celNum: { x: 150 * finer, y: 50 * finer, z: 1 }, simpleGrading: { x: 1, y: 0.2, z: 1 } })
blocks.push({ type: "hex", topology: [3, 6, 7, 4, 3, 6, 8, 5], celNum: { x: 30 * finer, y: 50 * finer, z: 1 }, simpleGrading: { x: 1, y: 0.2, z: 1 } })
blocks.push({ type: "hex", topology: [6, 9, 10, 7, 6, 9, 11, 8], celNum: { x: 20 * finer, y: 50 * finer, z: 1 }, simpleGrading: { x: 1, y: 0.2, z: 1 } })
blocks.push({ type: "hex", topology: [9, 12, 13, 10, 9, 12, 14, 11], celNum: { x: 50 * finer, y: 50 * finer, z: 1 }, simpleGrading: { x: 1, y: 0.2, z: 1 } })
blockMeshDict += blocksToString(blocks)
//定义edges字段(用于描述哪些边是圆弧)
var edges = []
edges.push({ type: "arc", topology: { p1: 10, p2: 7 }, midPoint: { x: L + x1 + x2, y: y2, z: -y2 * tanTheta } })
edges.push({ type: "arc", topology: { p1: 11, p2: 8 }, midPoint: { x: L + x1 + x2, y: y2, z: y2 * tanTheta } })
blockMeshDict += edgesToString(edges)
//定义boundary字段
var boundary = []
boundary.push({ name: "upWall", type: "wall", faces: [[5, 4, 1, 2], [5, 8, 7, 4], [8, 11, 10, 7], [11, 14, 13, 10]] })
boundary.push({ name: "leftWall", type: "wall", faces: [[0, 0, 2, 1]] })
boundary.push({ name: "rightWall", type: "patch", faces: [[12, 12, 13, 14]] })
boundary.push({ name: "front", type: "wedge", faces: [[0, 3, 5, 2], [3, 6, 8, 5], [6, 9, 11, 8], [9, 12, 14, 11]] })
boundary.push({ name: "back", type: "wedge", faces: [[1, 4, 3, 0], [4, 7, 6, 3], [7, 10, 9, 6], [10, 13, 12, 9]] })
blockMeshDict += boundaryToString(boundary)
console.log(blockMeshDict)
function verticesToString(vertices) {
let str = "\nvertices\n("
vertices.forEach(ele => {
str += `\n ( ${ele.x} ${ele.y} ${ele.z} )`
})
str += "\n);\n"
return str
}
function blocksToString(blocks) {
let str = "\nblocks\n("
blocks.forEach(ele => {
str += `\n ${ele.type} (`
ele.topology.forEach(ele => {
str += ` ${ele}`
})
str += `) (${ele.celNum.x} ${ele.celNum.y} ${ele.celNum.z})`
str += `simpleGrading (${ele.simpleGrading.x} ${ele.simpleGrading.y} ${ele.simpleGrading.z})`
})
str += "\n);\n"
return str
}
function edgesToString(edges) {
let str = "\nedges\n("
edges.forEach(ele => {
str += `\n ${ele.type} ${ele.topology.p1} ${ele.topology.p2} ( ${ele.midPoint.x} ${ele.midPoint.y} ${ele.midPoint.z} )`
})
str += "\n);\n"
return str
}
function boundaryToString(boundary) {
let str = "\nboundary\n("
boundary.forEach(ele => {
str += `\n ${ele.name}\n {\n type ${ele.type};\n faces\n (`
ele.faces.forEach(face => {
str += `\n ( `
face.forEach(vertice => {
str += `${vertice} `
})
str += ")"
})
str += "\n );"
str += "\n }"
})
str += "\n);\n"
return str
}
代码中依次生成了vertices字段、blocks字段、edges字段和boundary字段,并全部储存在blockMeshDict
字符串里。
最终将blockMeshDict
字符串输出到控制台上。输出为
/*--------------------------------*- C++ -*----------------------------------*\
========= |
\\ / F ield | OpenFOAM: The Open Source CFD Toolbox
\\ / O peration | Website: https://openfoam.org
\\ / A nd | Version: 8
\\/ M anipulation |
\*---------------------------------------------------------------------------*/
FoamFile
{
version 2.0;
format ascii;
class dictionary;
object blockMeshDict;
}
// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * //
convertToMeters 0.0254;
vertices
(
( -1 0 0 )
( -1 6 -0.10473038956930551 )
( -1 6 0.10473038956930551 )
( 20 0 0 )
( 20 6 -0.10473038956930551 )
( 20 6 0.10473038956930551 )
( 24.414213562373096 0 0 )
( 24.414213562373096 1.5857864376269049 -0.02768000523106449 )
( 24.414213562373096 1.5857864376269049 0.02768000523106449 )
( 26.34606521495123 0 0 )
( 26.34606521495123 1.0681483474218634 -0.01864459875721694 )
( 26.34606521495123 1.0681483474218634 0.01864459875721694 )
( 33.86263444133674 0 0 )
( 33.86263444133674 3.082207001484488 -0.05380012333311857 )
( 33.86263444133674 3.082207001484488 0.05380012333311857 )
);
blocks
(
hex ( 0 3 4 1 0 3 5 2) (150 50 1)simpleGrading (1 0.2 1)
hex ( 3 6 7 4 3 6 8 5) (30 50 1)simpleGrading (1 0.2 1)
hex ( 6 9 10 7 6 9 11 8) (20 50 1)simpleGrading (1 0.2 1)
hex ( 9 12 13 10 9 12 14 11) (50 50 1)simpleGrading (1 0.2 1)
);
edges
(
arc 10 7 ( 25.82842712474619 1 -0.017455064928217585 )
arc 11 8 ( 25.82842712474619 1 0.017455064928217585 )
);
boundary
(
upWall
{
type wall;
faces
(
( 5 4 1 2 )
( 5 8 7 4 )
( 8 11 10 7 )
( 11 14 13 10 )
);
}
leftWall
{
type wall;
faces
(
( 0 0 2 1 )
);
}
rightWall
{
type patch;
faces
(
( 12 12 13 14 )
);
}
front
{
type wedge;
faces
(
( 0 3 5 2 )
( 3 6 8 5 )
( 6 9 11 8 )
( 9 12 14 11 )
);
}
back
{
type wedge;
faces
(
( 1 4 3 0 )
( 4 7 6 3 )
( 7 10 9 6 )
( 10 13 12 9 )
);
}
);
使用方法
环境需求:nodejs
在命令行运行
node meshGenerator.js > blockMeshDict
将结果重定向到blockMeshDict文件
然后转到openFoam案例目录下,运行blockMesh
blockMesh
网格划分完毕之后,可使用paraview查看网格,运行
paraFoam
效果如下
用户可以通过修改js代码来对其他问题进行网格划分