def main(): import sys import fem_mesh fem_mesh.check_version() # lets read in some CLI arguments args = parse_cli() # find nodes in the structure and assign them to a dictionary structNodeIDs = findStructNodeIDs(args) # find elements that contain the structure nodes (elems, structElemIDs) = findStructElemIDs(args.elefile, structNodeIDs) # generate the new element file with the structure elements assigned the # new part ID NEFILE = open(args.nefile, 'w') NEFILE.write("$ Generated using %s with the following " "options:\n" % (sys.argv[0])) NEFILE.write("$ %s\n" % args) NEFILE.write('$ # Structure Nodes = %i\n' % structNodeIDs.__len__()) NEFILE.write('$ # Structure Elements = %i\n' % structElemIDs.__len__()) NEFILE.write('*ELEMENT_SOLID\n') for i in elems: if i[0] in structElemIDs: i[1] = args.partid j = i.tolist() NEFILE.write('%s\n' % ','.join('%i' % val for val in j[0:10])) NEFILE.write('*END') NEFILE.close()
def main(): import fem_mesh fem_mesh.check_version() args = parse_cli() struct_type = define_struct_type(args) structNodeIDs = findStructNodeIDs(args.nodefile, struct_type, args.sopts) (elems, structElemIDs) = findStructElemIDs(args.elefile, structNodeIDs) write_struct_elems(args.nefile, args.partid, elems, structNodeIDs, structElemIDs)
def main(): import sys import fem_mesh fem_mesh.check_version() # read in CLI arguments args = parse_cli() # generate node & element output files out_file_header = ("$ Generated using %s:\n$ %s\n$" % (sys.argv[0], args)) pos = calc_node_pos(args.xyz, args.numElem) writeNodes(pos, args.nodefile, out_file_header) writeElems(args.numElem, args.partid, args.elefile, out_file_header)
def main(): import sys import fem_mesh fem_mesh.check_version() # read in CLI arguments args = parse_cli() xyz = args.xyz numElem = args.numElem nodefile = args.nodefile partid = args.partid elefile = args.elefile run(xyz, numElem, nodefile, elefile, partid) return 0
def main(): """ """ from fem_mesh import check_version check_version() opts = read_cli() loadfilename = ("gauss_exc_sigma_%.3f_%.3f_%.3f_" "center_%.3f_%.3f_%.3f_amp_%.3f_amp_cut_%.3f_%s.dyn" % (opts.sigma[0], opts.sigma[1], opts.sigma[2], opts.center[0], opts.center[1], opts.center[2], opts.amp, opts.amp_cut, opts.sym)) generate_loads(opts.sigma, opts.center, opts.amp, opts.amp_cut, opts.sym, opts.direction, loadfilename, opts.nodefile) return 0
def main(): import fem_mesh import sys fem_mesh.check_version() opts = read_cli() if opts.pml: pmlfile = create_pml_elems_file(opts.elefile) BCFILE = open_bcfile(opts, sys.argv[0]) nodeIDcoords = load_nodeIDs_coords(opts.nodefile) [snic, axes] = fem_mesh.SortNodeIDs(nodeIDcoords) axdiff = [axes[0][1]-axes[0][0], axes[1][1]-axes[1][0], axes[2][1]-axes[2][0]] segID = 1 # BACK axis = 0 axis_limit = axes[0].min() planeNodeIDs = fem_mesh.extractPlane(snic, axes, (axis, axis_limit)) if opts.nonreflect: segID = writeSeg(BCFILE, 'BACK', segID, planeNodeIDs) elif opts.pml: apply_pml(opts.nodefile, pmlfile, BCFILE, planeNodeIDs, axis, axis_limit, axis_limit+opts.num_pml_elems*axdiff[axis], opts.pml_partID) # FRONT axis = 0 axis_limit = axes[0].max() planeNodeIDs = fem_mesh.extractPlane(snic, axes, (axis, axis_limit)) if (opts.sym == 'q') or (opts.sym == 'h'): # no top / bottom rows (those will be defined in the # top/bottom defs) writeNodeBC(BCFILE, planeNodeIDs[1:-1], '1,0,0,0,1,1') else: if opts.nonreflect: segID = writeSeg(BCFILE, 'FRONT', segID, planeNodeIDs) elif opts.pml: apply_pml(opts.nodefile, pmlfile, BCFILE, planeNodeIDs, axis, axis_limit-opts.num_pml_elems*axdiff[axis], axis_limit, opts.pml_partID) # LEFT (push side; non-reflecting or symmetry) axis = 1 axis_limit = axes[1].min() planeNodeIDs = fem_mesh.extractPlane(snic, axes, (axis, axis_limit)) # if quarter-symmetry, then apply BCs, in addition to a # modified edge; and don't deal w/ top/bottom if opts.sym == 'q': writeNodeBC(BCFILE, planeNodeIDs[1:-1], '0,1,0,1,0,1') # else make it a non-reflecting boundary else: if opts.nonreflect: segID = writeSeg(BCFILE, 'LEFT', segID, planeNodeIDs) elif opts.pml: apply_pml(opts.nodefile, pmlfile, BCFILE, planeNodeIDs, axis, axis_limit, axis_limit+opts.num_pml_elems*axdiff[axis], opts.pml_partID) # RIGHT (non-reflecting) axis = 1 axis_limit = axes[1].max() planeNodeIDs = fem_mesh.extractPlane(snic, axes, (axis, axis_limit)) if opts.nonreflect: segID = writeSeg(BCFILE, 'RIGHT', segID, planeNodeIDs) elif opts.pml: apply_pml(opts.nodefile, pmlfile, BCFILE, planeNodeIDs, axis, axis_limit-opts.num_pml_elems*axdiff[axis], axis_limit, opts.pml_partID) # BOTTOM axis = 2 axis_limit = axes[2].min() planeNodeIDs = fem_mesh.extractPlane(snic, axes, (axis, axis_limit)) if opts.nonreflect: segID = writeSeg(BCFILE, 'BOTTOM', segID, planeNodeIDs) if opts.bottom == 'full': writeNodeBC(BCFILE, planeNodeIDs, '1,1,1,1,1,1') elif opts.bottom == 'inplane': writeNodeBC(BCFILE, planeNodeIDs, '0,0,1,1,1,0') elif opts.pml: apply_pml(opts.nodefile, pmlfile, BCFILE, planeNodeIDs, axis, axis_limit, axis_limit+opts.num_pml_elems*axdiff[axis], opts.pml_partID) # TOP (transducer face) axis = 2 axis_limit = axes[2].max() planeNodeIDs = fem_mesh.extractPlane(snic, axes, (axis, axis_limit)) if opts.nonreflect: segID = writeSeg(BCFILE, 'TOP', segID, planeNodeIDs) if opts.top: writeNodeBC(BCFILE, planeNodeIDs, '1,1,1,1,1,1') elif opts.pml: apply_pml(opts.nodefile, pmlfile, BCFILE, planeNodeIDs, axis, axis_limit-opts.num_pml_elems*axdiff[axis], axis_limit, opts.pml_partID) if opts.nonreflect: write_nonreflecting(BCFILE, segID) BCFILE.close()
def main(): import fem_mesh import sys fem_mesh.check_version() opts = read_cli() BCFILE = open_bcfile(opts, sys.argv[0]) nodeIDcoords = load_nodeIDs_coords(opts.nodefile) [snic, axes] = fem_mesh.SortNodeIDs(nodeIDcoords) segID = 1 # BACK plane = (0, axes[0].min()) planeNodeIDs = fem_mesh.extractPlane(snic, axes, plane) segID = writeSeg(BCFILE, 'BACK', segID, planeNodeIDs) # FRONT plane = (0, axes[0].max()) planeNodeIDs = fem_mesh.extractPlane(snic, axes, plane) if (opts.sym == 'q') or (opts.sym == 'h'): # no top / bottom rows (those will be defined in the # top/bottom defs) writeNodeBC(BCFILE, planeNodeIDs[1:-1], '1,0,0,0,1,1') else: segID = writeSeg(BCFILE, 'FRONT', segID, planeNodeIDs) # LEFT (push side; non-reflecting or symmetry) plane = (1, axes[1].min()) planeNodeIDs = fem_mesh.extractPlane(snic, axes, plane) # if quarter-symmetry, then apply BCs, in addition to a # modified edge; and don't deal w/ top/bottom if opts.sym == 'q': writeNodeBC(BCFILE, planeNodeIDs[1:-1], '0,1,0,1,0,1') # else make it a non-reflecting boundary else: segID = writeSeg(BCFILE, 'LEFT', segID, planeNodeIDs) # RIGHT (non-reflecting) plane = (1, axes[1].max()) planeNodeIDs = fem_mesh.extractPlane(snic, axes, plane) segID = writeSeg(BCFILE, 'RIGHT', segID, planeNodeIDs) # BOTTOM plane = (2, axes[2].min()) planeNodeIDs = fem_mesh.extractPlane(snic, axes, plane) segID = writeSeg(BCFILE, 'BOTTOM', segID, planeNodeIDs) if opts.bottom == 'full': writeNodeBC(BCFILE, planeNodeIDs, '1,1,1,1,1,1') elif opts.bottom == 'inplane': writeNodeBC(BCFILE, planeNodeIDs, '0,0,1,1,1,0') # TOP (transducer face) plane = (2, axes[2].max()) planeNodeIDs = fem_mesh.extractPlane(snic, axes, plane) segID = writeSeg(BCFILE, 'TOP', segID, planeNodeIDs) if opts.top: writeNodeBC(BCFILE, planeNodeIDs, '1,1,1,1,1,1') write_nonreflecting(BCFILE, segID) BCFILE.close()
def main(): import sys import numpy as n from bc import SortNodeIDs, extractPlane import fem_mesh fem_mesh.check_version() opts = read_cli() loadtype = opts.loadtype direction = int(opts.direction) amplitude = float(opts.amplitude) lcid = int(opts.lcid) # open the top load file to write LOADFILE = open(opts.loadfile, 'w') if loadtype == 'disp' or loadtype == 'vel' or loadtype == 'accel': LOADFILE.write("*BOUNDARY_PRESCRIBED_MOTION_NODE\n") elif loadtype == 'force': LOADFILE.write("*LOAD_NODE_POINT\n") else: sys.exit('ERROR: Invalid loadtype specified (can only be disp, ' 'force, vel or accel)') LOADFILE.write("$ Generated using %s with the following " "options:\n" % sys.argv[0]) LOADFILE.write("$ %s\n" % opts) # load in all of the node data, excluding '*' lines header_comment_skips = fem_mesh.count_header_comment_skips(opts.nodefile) nodeIDcoords = n.loadtxt(opts.nodefile, delimiter=',', skiprows=header_comment_skips, comments='*', dtype=[('id', 'i4'), ('x', 'f4'), ('y', 'f4'), ('z', 'f4')]) # there are 6 faces in these models; we need to (1) find the top face and # (2) apply the appropriate loads [snic, axes] = SortNodeIDs(nodeIDcoords) # extract spatially-sorted node IDs on a the top z plane plane = (2, axes[2].max()) planeNodeIDs = extractPlane(snic, axes, plane) # write out nodes on the top z plane with corresponding load values # (direction of motion, nodal displacement (accel, vel, etc), temporal load # curve ID, scale factor for load curve) # TODO: would like to clean this up with a dictionary to associate the # prescribed motions with their integer IDs with one statement instead of # three conditional statements below if loadtype == 'disp': writeNodeLoads(LOADFILE, planeNodeIDs, '%i,2,%i,%f' % (direction, lcid, amplitude)) elif loadtype == 'vel': writeNodeLoads(LOADFILE, planeNodeIDs, '%i,0,%i,%f' % (direction, lcid, amplitude)) elif loadtype == 'accel': writeNodeLoads(LOADFILE, planeNodeIDs, '%i,1,%i,%f' % (direction, lcid, amplitude)) elif loadtype == 'force': writeNodeLoads(LOADFILE, planeNodeIDs, '%i,%i,%f' % (direction, lcid, amplitude)) LOADFILE.write("*END\n") # close all of our files open for read/write LOADFILE.close()
def main(): """ Generate Guassian-weighted point load distribution """ fem_mesh.check_version() opts = read_cli() # setup the new output file with a very long, but unique, filename loadfilename = ("gauss_exc_sigma_%.3f_%.3f_%.3f_center_%.3f_%.3f_%.3f_amp_%.3f_amp_cut_%.3f_%s.dyn" % (opts.sigma[0], opts.sigma[1], opts.sigma[2], opts.center[0], opts.center[1], opts.center[2], opts.amp, opts.amp_cut, opts.sym)) LOADFILE = open(loadfilename, 'w') LOADFILE.write("$ Generated using %s:\n" % sys.argv[0]) LOADFILE.write("$ %s\n" % opts) LOADFILE.write("*LOAD_NODE_POINT\n") # loop through all of the nodes and see which ones fall w/i the Gaussian # excitation field sym_node_count = 0 node_count = 0 NODEFILE = open(opts.nodefile,'r') for i in NODEFILE: # make sure not to process comment and command syntax lines if i[0] != "$" and i[0] != "*": i = i.rstrip('\n') # dyna scripts should be kicking out comma-delimited data; if not, # then the user needs to deal with it fields = i.split(',') fields = [float(j) for j in fields] # check for unexpected inputs and exit if needed (have user figure # out what's wrong) if len(fields) != 4: print("ERROR: Unexpected number of node columns") print(fields) sys.exit(1) # compute the Gaussian amplitude at the node exp1 = math.pow((fields[1]-opts.center[0])/opts.sigma[0], 2) exp2 = math.pow((fields[2]-opts.center[1])/opts.sigma[1], 2) exp3 = math.pow((fields[3]-opts.center[2])/opts.sigma[2], 2) nodeGaussAmp = opts.amp * math.exp(-(exp1 + exp2 + exp3)) # write the point load only if the amplitude is above the cutoff # dyna input needs to be limited in precision if nodeGaussAmp > opts.amp*opts.amp_cut: node_count += 1 # check for quarter symmetry force reduction (if needed) if opts.sym == 'qsym': if (math.fabs(fields[1]) < opts.search_tol and math.fabs(fields[2]) < opts.search_tol): nodeGaussAmp = nodeGaussAmp/4 sym_node_count += 1 elif (math.fabs(fields[1]) < opts.search_tol or math.fabs(fields[2]) < opts.search_tol): nodeGaussAmp = nodeGaussAmp/2 sym_node_count += 1 # check for half symmetry force reduction (if needed) elif opts.sym == 'hsym': if math.fabs(fields[1]) < opts.search_tol: nodeGaussAmp = nodeGaussAmp/2 sym_node_count += 1 elif opts.sym != 'none': sys.exit('ERROR: Invalid symmetry option specified.') LOADFILE.write("%i,3,1,-%.4f\n" % (int(fields[0]), nodeGaussAmp)) # wrap everything up NODEFILE.close() LOADFILE.write("*END\n") LOADFILE.write("$ %i loads generated\n" % node_count) LOADFILE.write("$ %i exist on a symmetry plane / edge\n" % sym_node_count) LOADFILE.close()
def main(): import fem_mesh import sys fem_mesh.check_version() opts = read_cli() if opts.pml: pmlfile = create_pml_elems_file(opts.elefile) BCFILE = open_bcfile(opts, sys.argv[0]) nodeIDcoords = load_nodeIDs_coords(opts.nodefile) [snic, axes] = fem_mesh.SortNodeIDs(nodeIDcoords) axdiff = [ axes[0][1] - axes[0][0], axes[1][1] - axes[1][0], axes[2][1] - axes[2][0] ] segID = 1 # BACK axis = 0 axis_limit = axes[0].min() planeNodeIDs = fem_mesh.extractPlane(snic, axes, (axis, axis_limit)) if opts.nonreflect: segID = writeSeg(BCFILE, 'BACK', segID, planeNodeIDs) elif opts.pml: apply_pml(opts.nodefile, pmlfile, BCFILE, planeNodeIDs, axis, axis_limit, axis_limit + opts.num_pml_elems * axdiff[axis], opts.pml_partID) # FRONT axis = 0 axis_limit = axes[0].max() planeNodeIDs = fem_mesh.extractPlane(snic, axes, (axis, axis_limit)) if (opts.sym == 'q') or (opts.sym == 'h'): # no top / bottom rows (those will be defined in the # top/bottom defs) writeNodeBC(BCFILE, planeNodeIDs[1:-1], '1,0,0,0,1,1') else: if opts.nonreflect: segID = writeSeg(BCFILE, 'FRONT', segID, planeNodeIDs) elif opts.pml: apply_pml(opts.nodefile, pmlfile, BCFILE, planeNodeIDs, axis, axis_limit - opts.num_pml_elems * axdiff[axis], axis_limit, opts.pml_partID) # LEFT (push side; non-reflecting or symmetry) axis = 1 axis_limit = axes[1].min() planeNodeIDs = fem_mesh.extractPlane(snic, axes, (axis, axis_limit)) # if quarter-symmetry, then apply BCs, in addition to a # modified edge; and don't deal w/ top/bottom if opts.sym == 'q': writeNodeBC(BCFILE, planeNodeIDs[1:-1], '0,1,0,1,0,1') # else make it a non-reflecting boundary else: if opts.nonreflect: segID = writeSeg(BCFILE, 'LEFT', segID, planeNodeIDs) elif opts.pml: apply_pml(opts.nodefile, pmlfile, BCFILE, planeNodeIDs, axis, axis_limit, axis_limit + opts.num_pml_elems * axdiff[axis], opts.pml_partID) # RIGHT (non-reflecting) axis = 1 axis_limit = axes[1].max() planeNodeIDs = fem_mesh.extractPlane(snic, axes, (axis, axis_limit)) if opts.nonreflect: segID = writeSeg(BCFILE, 'RIGHT', segID, planeNodeIDs) elif opts.pml: apply_pml(opts.nodefile, pmlfile, BCFILE, planeNodeIDs, axis, axis_limit - opts.num_pml_elems * axdiff[axis], axis_limit, opts.pml_partID) # BOTTOM axis = 2 axis_limit = axes[2].min() planeNodeIDs = fem_mesh.extractPlane(snic, axes, (axis, axis_limit)) if opts.nonreflect: segID = writeSeg(BCFILE, 'BOTTOM', segID, planeNodeIDs) if opts.bottom == 'full': writeNodeBC(BCFILE, planeNodeIDs, '1,1,1,1,1,1') elif opts.bottom == 'inplane': writeNodeBC(BCFILE, planeNodeIDs, '0,0,1,1,1,0') elif opts.pml: apply_pml(opts.nodefile, pmlfile, BCFILE, planeNodeIDs, axis, axis_limit, axis_limit + opts.num_pml_elems * axdiff[axis], opts.pml_partID) # TOP (transducer face) axis = 2 axis_limit = axes[2].max() planeNodeIDs = fem_mesh.extractPlane(snic, axes, (axis, axis_limit)) if opts.nonreflect: segID = writeSeg(BCFILE, 'TOP', segID, planeNodeIDs) if opts.top: writeNodeBC(BCFILE, planeNodeIDs, '1,1,1,1,1,1') elif opts.pml: apply_pml(opts.nodefile, pmlfile, BCFILE, planeNodeIDs, axis, axis_limit - opts.num_pml_elems * axdiff[axis], axis_limit, opts.pml_partID) if opts.nonreflect: write_nonreflecting(BCFILE, segID) BCFILE.close()
def main(): """ Generate Guassian-weighted point load distribution """ fem_mesh.check_version() opts = read_cli() # setup the new output file with a very long, but unique, filename loadfilename = ( "gauss_exc_sigma_%.3f_%.3f_%.3f_center_%.3f_%.3f_%.3f_amp_%.3f_amp_cut_%.3f_%s.dyn" % (opts.sigma[0], opts.sigma[1], opts.sigma[2], opts.center[0], opts.center[1], opts.center[2], opts.amp, opts.amp_cut, opts.sym)) LOADFILE = open(loadfilename, 'w') LOADFILE.write("$ Generated using %s:\n" % sys.argv[0]) LOADFILE.write("$ %s\n" % opts) LOADFILE.write("*LOAD_NODE_POINT\n") # loop through all of the nodes and see which ones fall w/i the Gaussian # excitation field sym_node_count = 0 node_count = 0 NODEFILE = open(opts.nodefile, 'r') for i in NODEFILE: # make sure not to process comment and command syntax lines if i[0] != "$" and i[0] != "*": i = i.rstrip('\n') # dyna scripts should be kicking out comma-delimited data; if not, # then the user needs to deal with it fields = i.split(',') fields = [float(j) for j in fields] # check for unexpected inputs and exit if needed (have user figure # out what's wrong) if len(fields) != 4: print("ERROR: Unexpected number of node columns") print(fields) sys.exit(1) # compute the Gaussian amplitude at the node exp1 = math.pow((fields[1] - opts.center[0]) / opts.sigma[0], 2) exp2 = math.pow((fields[2] - opts.center[1]) / opts.sigma[1], 2) exp3 = math.pow((fields[3] - opts.center[2]) / opts.sigma[2], 2) nodeGaussAmp = opts.amp * math.exp(-(exp1 + exp2 + exp3)) # write the point load only if the amplitude is above the cutoff # dyna input needs to be limited in precision if nodeGaussAmp > opts.amp * opts.amp_cut: node_count += 1 # check for quarter symmetry force reduction (if needed) if opts.sym == 'qsym': if (math.fabs(fields[1]) < opts.search_tol and math.fabs(fields[2]) < opts.search_tol): nodeGaussAmp = nodeGaussAmp / 4 sym_node_count += 1 elif (math.fabs(fields[1]) < opts.search_tol or math.fabs(fields[2]) < opts.search_tol): nodeGaussAmp = nodeGaussAmp / 2 sym_node_count += 1 # check for half symmetry force reduction (if needed) elif opts.sym == 'hsym': if math.fabs(fields[1]) < opts.search_tol: nodeGaussAmp = nodeGaussAmp / 2 sym_node_count += 1 elif opts.sym != 'none': sys.exit('ERROR: Invalid symmetry option specified.') LOADFILE.write("%i,3,1,-%.4f\n" % (int(fields[0]), nodeGaussAmp)) # wrap everything up NODEFILE.close() LOADFILE.write("*END\n") LOADFILE.write("$ %i loads generated\n" % node_count) LOADFILE.write("$ %i exist on a symmetry plane / edge\n" % sym_node_count) LOADFILE.close()