ace-mini-1 / scripts /mesh_prediction_step.py
ConnorKapoor's picture
Deploy isolated Ace-Mini research preview
b1b1e02 verified
Raw History Blame Contribute Delete
1.93 kB
"""Generate a CAD-conforming display volume. This is not a CFD solve."""
import sys,json,time
from pathlib import Path
import gmsh,numpy as np
p=Path(sys.argv[1]);start=time.perf_counter()
gmsh.initialize();gmsh.option.setNumber('General.Terminal',0)
try:
gmsh.model.occ.importShapes(str(p/'input.step'));gmsh.model.occ.synchronize()
box=np.array(gmsh.model.getBoundingBox(-1,-1));extent=box[3:]-box[:3];h=float(max(extent)/28)
gmsh.option.setNumber('Mesh.MeshSizeMax',h);gmsh.option.setNumber('Mesh.MeshSizeMin',h/3)
gmsh.option.setNumber('Mesh.MeshSizeFromCurvature',12);gmsh.option.setNumber('Mesh.ElementOrder',1)
gmsh.model.mesh.generate(3)
ids,coords,_=gmsh.model.mesh.getNodes();v=np.asarray(coords).reshape(-1,3);lookup={int(n):i for i,n in enumerate(ids)}
def elements(dim,typ):
kinds,_,nodes=gmsh.model.mesh.getElements(dim);x=nodes[list(kinds).index(typ)];return np.array([lookup[int(i)] for i in x]).reshape(-1,dim+1)
tet=elements(3,4);faces=elements(2,2)
reference=json.loads((p/'geometry.json').read_text());actual=np.ptp(v,axis=0)
if not np.allclose(actual,reference['dimensions_mm'],rtol=.02,atol=.3):raise ValueError('Display mesh and STEP reader disagree on dimensions or units')
corners=v[tet];volume=float(np.abs(np.linalg.det(corners[:,1:]-corners[:,:1])).sum()/6);error=abs(volume-reference['volume_mm3'])/reference['volume_mm3']
if error>.1:raise ValueError('Display mesh volume differs from the CAD solid by over 10%; a finer mesh is required')
if len(v)>80000 or len(tet)>400000:raise ValueError('Display volume exceeds memory budget')
np.savez_compressed(p/'volume.npz',vertices=v,tetrahedra=tet,triangles=faces)
(p/'volume.json').write_text(json.dumps({'nodes':len(v),'tetrahedra':len(tet),'surface_triangles':len(faces),'method':'CAD-conforming first-order Gmsh tetrahedra, display only','volume_error_fraction':error,'seconds':time.perf_counter()-start}))
finally:gmsh.finalize()