Gmsh中复制平移结构化曲面后transfinite属性丢失问题咨询
解决Gmsh复制平移后Transfinite属性丢失的问题
这个问题我之前也碰到过——Gmsh的复制操作确实不会自动继承原始实体的网格约束,比如transfinite这类设置,因为复制出来的是全新的独立实体,和原始对象没有属性关联。不过咱们可以通过脚本批量处理的方式,让复制后的结构也保留结构化四边形网格,下面给你具体的解决思路和代码示例:
核心原因
Transfinite是直接绑定在**原始几何实体(线、面)**上的网格生成规则,当你复制平移时,Gmsh只会复制几何形状,不会把这些网格属性一并复制过去,所以需要手动给新生成的实体重新设置这些规则。
.geo脚本解决方案(适合快速测试)
先写原始方形的定义和transfinite设置,然后用循环复制,再批量给复制后的面和线添加transfinite约束:
SetFactory("OpenCASCADE"); // 1. 定义原始方形并设置结构化网格 Point(1) = {0, 0, 0, 1.0}; Point(2) = {1, 0, 0, 1.0}; Point(3) = {1, 1, 0, 1.0}; Point(4) = {0, 1, 0, 1.0}; Line(1) = {1,2}; Line(2) = {2,3}; Line(3) = {3,4}; Line(4) = {4,1}; Curve Loop(1) = {1,2,3,4}; Plane Surface(1) = {1}; // 给原始方形的线和面设置transfinite Transfinite Line{1,2,3,4} = 10 Using Progression 1; Transfinite Surface{1}; Recombine Surface{1}; // 2. 循环复制并平移(这里复制3次,每次X方向平移1.5) For i In {1:3} Translate {i*1.5, 0, 0} {Duplicata{Surface{1};}} EndFor // 3. 给复制后的面批量设置transfinite For i In {2:4} // 复制后的面ID是2、3、4 // 自动获取当前面的所有边界线 LinesOfSurface(i) = l[]; // 给边界线设置transfinite Transfinite Line{l[]} = 10 Using Progression 1; // 设置面的transfinite并重组为四边形 Transfinite Surface{i}; Recombine Surface{i}; EndFor
这里关键是用LinesOfSurface(i)函数自动获取面的所有边界线,不用手动记线的ID,非常适合批量处理。
Python API解决方案(适合复杂自动化场景)
如果你的结构更复杂,用Python API会更灵活,能动态处理任意数量的复制:
import gmsh gmsh.initialize() gmsh.option.setNumber("General.Terminal", 1) gmsh.model.add("structured_grid_copy") # 1. 创建原始方形并设置结构化网格 p1 = gmsh.model.geo.addPoint(0, 0, 0, 1.0) p2 = gmsh.model.geo.addPoint(1, 0, 0, 1.0) p3 = gmsh.model.geo.addPoint(1, 1, 0, 1.0) p4 = gmsh.model.geo.addPoint(0, 1, 0, 1.0) l1 = gmsh.model.geo.addLine(p1, p2) l2 = gmsh.model.geo.addLine(p2, p3) l3 = gmsh.model.geo.addLine(p3, p4) l4 = gmsh.model.geo.addLine(p4, p1) cl1 = gmsh.model.geo.addCurveLoop([l1, l2, l3, l4]) s1 = gmsh.model.geo.addPlaneSurface([cl1]) # 设置原始面的transfinite约束 for line_id in [l1, l2, l3, l4]: gmsh.model.geo.mesh.setTransfiniteCurve(line_id, 10) gmsh.model.geo.mesh.setTransfiniteSurface(s1) gmsh.model.geo.mesh.recombine(s1) # 2. 批量复制平移 total_copies = 3 surfaces = [s1] for idx in range(total_copies): # 复制原始面 new_surfs = gmsh.model.geo.copy([(2, s1)]) # (2, id)表示维度为2的面实体 # 平移复制后的面(X方向每次偏移1.5) gmsh.model.geo.translate(new_surfs, ((idx+1)*1.5, 0, 0)) # 记录新面的ID surfaces.append(new_surfs[0][1]) # 3. 给所有复制后的面设置transfinite for surf_id in surfaces[1:]: # 获取当前面的所有边界线 boundary_lines = gmsh.model.geo.getBoundary([(2, surf_id)], oriented=False) line_ids = [line[1] for line in boundary_lines] # 给每条边界线设置transfinite for line_id in line_ids: gmsh.model.geo.mesh.setTransfiniteCurve(line_id, 10) # 设置面的transfinite并重组为四边形 gmsh.model.geo.mesh.setTransfiniteSurface(surf_id) gmsh.model.geo.mesh.recombine(surf_id) # 同步模型并生成网格 gmsh.model.geo.synchronize() gmsh.model.mesh.generate(2) gmsh.write("structured_copy.msh") gmsh.finalize()
关键注意点
- 必须给每个复制面的所有边界线都设置
Transfinite Line,否则面无法生成结构化网格; Recombine命令是将三角形网格转换为四边形的关键,不能省略;- 复制时要用
Duplicata(.geo)或copy(Python),而不是重新创建几何,这样能保证拓扑结构一致,更方便后续处理。
内容的提问来源于stack exchange,提问作者lmr
相关产品推荐
相关产品推荐

