众所周知,当然你也可以不知,哈哈,目前我知道的球的六面体网格有三种画法,文章中所述的应该属于较难的那种,各种切分,合并,然后使得模型形成可映射的结构,所以球的六面体网格在hm中对于新手而言是一个很不错的练习项
声明 :
1、如果你是用这个代码只为了来生成球的六面体网格做分析用,我个人建议去Lsdyna的前后处理软件LS-prepost里面直接一键生成个球网格,这个网格很漂亮,导出K文件即可
2、如果没有安装Lsdyna没关系,用ANSYS Workbench也可以设置多区网格划分方法生成质量不错的球
3、如果没有安装ANSYS,那就用我写的代码生成吧,毕竟Hypermesh画个漂亮的球六面体网格挺费劲
这个代码中有几个问题,我懒得改了,正在学习hm二开的读者可以一试
1、这个运行时候只能新建一个hm文件,如果使用存在comp的文件会报错,这个是因为我写的时候没有判断是否存在comp,正式写程序的时候首要就是要判断
2、如果在一个hm文件中生成2次不同半径的球网格也会报错,因为我在留下八分之一的球几何时候是通过Solid的ID来的,正常要通过坐标来定位到要留下的Solid
3、我使用不同的Hypermesh版本试了一下这个代码的网格生成能力,发现14版本和2022版本生成的球网格很规整,雅可比高,网格质量不错,但是用2022.3版本发现网格生成的雅可比较低,可能是基础的网格算法 会有些差异
最后,代码共享出来也欢迎学Hypermesh二次开发的伙伴一起交流,共同进步,后面慢慢转到Dyna上
在Hypermesh2022版本生成的效果如下:
代码不长,你以为我只为了给你生成个球网格?
# 1、创建 0 0 0点建立球
# 2、按照0 0 0点进行切分,留下1/8球体
# 3、给留下的球体的每个边创建一个中点
# 4、使用创建正方形命令,创建方块,然后进行布尔运算
# 5、根据正方形的定点找到线,然后判断线是否为共享边,把不是共享边的选中
# 6、根据选中的线,以及两个方向矢量去切分,共切三次
# 7、切分之后把切分成的体,根据node的位置找到,两两合并
# 8、六面体网格划分并镜像
# 9、删除2D网格,清除临时节点
# **************************
# hm_measureshortestdistance2 -5 0 -5 nodes 1 0 0
# *createmark lines 1 "by points"
# hm_measureshortestdistance2 -5 0 -5 points 1 0 0
# hm_writeviewcommands 0
# hm_highlightmark lines 1 "h"
# hm_entityinfo maxid solids
# hm_latestentityid comps
# **************************
namespace eval ::Model::MeshCreate {
}
proc ::Model::MeshCreate::Sphere3DMesh {radius meshsize} {
set originPoint "0 0 0"
set tol 0.1
*fixedpointhandle 1
set SphereCompName "Sphere_radius@$radius\mm"
foreach {x y z} $originPoint {}
# *createnode $x $y $z
#正方形的三个点
set Point1 "[expr ($radius/2)] $y $z"
set Point2 "$x $y [expr ($radius/2)]"
set Point3 "$x [expr ($radius/2)] $z"
*createentity comps name=$SphereCompName
# set SphereCompName [hm_getvalue comps id=[hm_latestentityid comps] dataname=name ]
# set SphereCompName [*setvalue comps name=$SphereCompName name=Sphere_radius@$radius\mm]
*solidspherefull $x $y $z $radius
puts "==========================SphereCreate is Done!========================"
#沿着XYZ分别切分
*createmark solids 1 "by comps name" $SphereCompName
*createplane 1 0 1 0 $x $y $z
*body_splitmerge_with_plane solids 1 1
*createmark solids 1 "by comps name" $SphereCompName
*createplane 1 1 0 0 $x $y $z
*body_splitmerge_with_plane solids 1 1
*createmark solids 1 "by comps name" $SphereCompName
*createplane 1 0 0 1 $x $y $z
*body_splitmerge_with_plane solids 1 1
#留下1/8球体
set retin [hm_entityinfo maxid solids]
*createmark solids 1 "by comps name" $SphereCompName
hm_markremove solids 1 $retin
set remove [hm_getmark solids 1]
*createmark solids 1 {*}$remove
*deletesolidswithelems 1 0 1
puts "==========================1/8 Model is Done!========================"
#单独显示球的comp
*createmark components 2 $SphereCompName
*createstringarray 2 "elements_on" "geometry_on"
*isolateentitybymark 2 1 2
#建立正方形
# *createmark lines 1 "displayed"
# *nodecreateonlines lines 1 1 0 0
foreach {x1 y1 z1} $Point1 {}
foreach {x2 y2 z2} $Point2 {}
foreach {x3 y3 z3} $Point3 {}
*solidblock $x $y $z $x1 $y1 $z1 $x2 $y2 $z2 $x3 $y3 $z3
puts "==========================BlockCreate is Done!========================"
set BlockID [hm_latestentityid solids]
#布尔求差
*createmark solids 1 $retin
*createmark solids 2 $BlockID
*boolean_merge_solids 1 2 14 1
set BlockID [hm_latestentityid solids]
#切割
set Point4 "[expr ($radius/2)] [expr ($radius/2)] $z"
set Point5 "$x [expr ($radius/2)] [expr ($radius/2)]"
set Point6 "[expr ($radius/2)] $y [expr ($radius/2)]"
foreach {x4 y4 z4} $Point4 {}
foreach {x5 y5 z5} $Point5 {}
foreach {x6 y6 z6} $Point6 {}
*createmark points 1 "displayed"
set Point4_id [lindex [hm_measureshortestdistance2 $x4 $y4 $z4 points 1 0 0] 4 ]
set Point5_id [lindex [hm_measureshortestdistance2 $x5 $y5 $z5 points 1 0 0] 4 ]
set Point6_id [lindex [hm_measureshortestdistance2 $x6 $y6 $z6 points 1 0 0] 4 ]
set Pointsid [list $Point4_id $Point5_id $Point6_id]
set LineUseful [list]
#筛选出3根用来切割的直线
foreach Pointid $Pointsid {
*createmark lines 1 "by points" $Pointid
set Linelist [hm_getmark lines 1]
foreach Line $Linelist {
set line_type [hm_getlinetype $Line]
if {$line_type == 2} {
lappend LineUseful $Line
}
}
}
#puts $LineUseful
set CutLine1 [lindex $LineUseful 0]
set CutLine2 [lindex $LineUseful 1]
set CutLine3 [lindex $LineUseful 2]
*createmark lines 1 $CutLine1 $CutLine2 $CutLine3
*linefromsurfedgecomp lines 1 0
set CutLine1 [hm_latestentityid lines 2]
set CutLine2 [hm_latestentityid lines 1]
set CutLine3 [hm_latestentityid lines 0]
#找到三根最长的弧线
*createmark lines 1 "displayed"
set line_ids [hm_getmark lines 1]
set Curve [list]
foreach line_id $line_ids {
*createmark lines 1 $line_id
set config [catch {*createbestcirclecenternode lines 1 0 1 0} res ]
#config为0说明为弧线
if {$config == 0} {
lappend Curve $line_id
}
}
*createmark lines 1 {*}$Curve
*nodecreateonlines lines 1 1 0 0
#找到三根线上新建立的节点
*createmark nodes 1 "displayed"
set node1_id [lindex [hm_measureshortestdistance2 $x4 $y4 $z4 nodes 1 0 0] 4 ]
set node2_id [lindex [hm_measureshortestdistance2 $x5 $y5 $z5 nodes 1 0 0] 4 ]
set node3_id [lindex [hm_measureshortestdistance2 $x6 $y6 $z6 nodes 1 0 0] 4 ]
set nodeCoordValue [lindex [hm_nodevalue $node1_id] 0 0]
# 隐藏正方形块
*createmark solids 1 $BlockID
*maskentitymark solids 1 0
#切分球体
*createmark solids 1 "displayed"
*createmark lines 1 $CutLine2
*createvector 1 $nodeCoordValue $nodeCoordValue 0
*body_split_with_swept_lines solids 1 1 1 0 3
*createmark solids 1 "displayed"
*createmark lines 1 $CutLine1
*createvector 1 0 $nodeCoordValue $nodeCoordValue
*body_split_with_swept_lines solids 1 1 1 0 3
*createmark solids 1 "displayed"
*createmark lines 1 $CutLine3
*createvector 1 $nodeCoordValue 0 $nodeCoordValue
*body_split_with_swept_lines solids 1 1 1 0 3
#开始合并切分的solid
set test1Point "$tol [expr $radius+$tol] 0"
set test2Point "0 [expr $radius+$tol] $tol"
set test3Point "0 $tol [expr $radius+$tol]"
set test4Point "$tol 0 [expr $radius+$tol]"
set test5Point "[expr $radius+$tol] $tol 0"
set test6Point "[expr $radius+$tol] 0 $tol"
foreach {x7 y7 z7} $test1Point {}
foreach {x8 y8 z8} $test2Point {}
foreach {x9 y9 z9} $test3Point {}
foreach {x10 y10 z10} $test4Point {}
foreach {x11 y11 z11} $test5Point {}
foreach {x12 y12 z12} $test6Point {}
set TestPoints_A [list $test1Point $test3Point $test5Point]
set TestPoints_B [list $test2Point $test4Point $test6Point]
foreach A $TestPoints_A B $TestPoints_B {
foreach {A_x A_y A_z } $A {}
foreach {B_x B_y B_z } $B {}
*createmark solids 1 "displayed"
set Mergesolid1 [lindex [hm_measureshortestdistance2 $A_x $A_y $A_z solids 1 0 0] 4 ]
set Mergesolid2 [lindex [hm_measureshortestdistance2 $B_x $B_y $B_z solids 1 0 0] 4 ]
*createmark solids 1 $Mergesolid1
*createmark solids 2 $Mergesolid2
*boolean_merge_solids 1 2 14 3
*clearmark solids 1;*clearmark solids 2;
}
puts "==========================Splits is Done!========================"
#划分网格
*createmark surfaces 1 "on plane" $x4 $y4 $z4 0 0 1 0.01 1 0
*appendmark surfaces 1 "on plane" $x6 $y6 $z6 0 1 0 0.01 1 0
*appendmark surfaces 1 "on plane" $x5 $y5 $z5 1 0 0 0.01 1 0
set surf [hm_getmark surfs 1]
# puts $surf
*setedgedensitylinkwithaspectratio 0
*defaultmeshsurf 1 $meshsize 2 1 2 0 1 0 1
*createmark solids 1 "by comps name" $SphereCompName
*solidmap_solids_begin 1 829568 $meshsize
*solidmap_solids_end
# 沿X轴镜像
*createmark elements 1 "by comps name" $SphereCompName
*duplicateentities elements 1 2
*createplane 1 1 0 0 $x $y $z
*reflectmarkwithoption elements 2 1 0
*clearmark elems 1;*clearmark elems 2;
# 沿y轴镜像
*createmark elements 1 "by comps name" $SphereCompName
*duplicateentities elements 1 2
*createplane 1 0 1 0 $x $y $z
*reflectmarkwithoption elements 2 1 0
*clearmark elems 1;*clearmark elems 2;
# 沿z轴镜像
*createmark elements 1 "by comps name" $SphereCompName
*duplicateentities elements 1 2
*createplane 1 0 0 1 $x $y $z
*reflectmarkwithoption elements 2 1 0
*clearmark elems 1;*clearmark elems 2;
puts "==========================Mirror is Done!========================"
#删除2D网格
catch {*createmark elems 1 "by config" quad4 tria3
*deletemark elements 1 }
puts "==========================2D Mesh Delete is Done!========================"
#清除临时节点
*nodecleartempmark
puts "==========================TempNodes Clear is Done!========================"
#网格共节点
*createmark components 1 $SphereCompName
*equivalence components 1 0.01 1 0 0 0
hm_markclearall 1;hm_markclearall 2
puts "==========================3D Mesh is Done!========================"
*window 0 0 0 0 0
}
set radius 10
set meshsize 1
proc ::Model::MeshCreate::GUI {args} {
catch {destroy .window};
set Title Sphere_Mesh
set Newframe [frame .window ]
hm_framework addpanel $Newframe $Title
hm_framework drawpanel $Newframe
set lable1 [labelframe $Newframe.lable1 -text "Sphere 3D Mesh" -bd 2 -font hwtkBoldFont -fg red]
grid $lable1 -row 1 -column 0 -sticky nsew
set radius_lbl [hwtk::label $lable1.radius_lbl -text "Sphere radius:" ]
set meshSize_lbl [hwtk::label $lable1.meshSize_lbl -text "Mesh Size:" ]
set radius_ent [hwtk::entry $lable1.radius_ent -textvariable radius -width 10 ]
set meshSize [hwtk::entry $lable1.meshSize -textvariable meshsize -width 10 ]
grid $radius_lbl -row 1 -column 1 -padx 5 -pady 5
grid $meshSize_lbl -row 2 -column 1 -padx 5 -pady 5 -sticky nsew
grid $radius_ent -row 1 -column 2 -padx 5 -pady 5
grid $meshSize -row 2 -column 2 -padx 5 -pady 5
grid [ttk::button $lable1.runbtn -text "Run" -command {::Model::MeshCreate::Sphere3DMesh $radius $meshsize}\
-width 10 ] -row 1 -column 3 -rowspan 30 -padx 5 -pady 5 -sticky ns
}
::Model::MeshCreate::GUI