# import necessary modules to handle Abaqus output database, files and string from odbAccess import * from textRepr import * from string import * import os import time def ConvertOdb2Vtk(): # Modify the default value of filename here to specify the default configuration file starttime = time.time() # display the reading result of odb2vtk file print("odb2vtk reading finished, time elapsed: "), time.time()-starttime print("Basic Information:") print("Model:", odb_path, "; Mesh type:", mesh_name, "; Number of blocks:", 1) print("Convert frames: ", input_frame[0], " to ", input_frame[-1]) print("Step & Instance : ", str(input_step), ", ", str(input_instance)) # open an ODB ( Abaqus output database ) odb = openOdb(os.path.join(odb_path), readOnly=True) print("ODB opened") # access geometry and topology information ( odb->rootAssembly->instances->(nodes, elements) ) rootassembly = odb.rootAssembly instance = rootassembly.instances # access attribute information step = odb.steps # get instance & step information : Quantity and all names allinstancestr = str(instance) autoins = allinstancestr.split("'") inslen = len(autoins)/4 instance_N = range(0, inslen) allstepstr = str(step) autostep = allstepstr.split("'") steplen = len(autostep)/4 step_N = range(0, steplen) for i in input_step: if (steplen < int(i)): print("input step exceeds the range of steps") os._exit(0) for i in input_instance: if (inslen < int(i)): print("input instance exceeds the range of instances") os._exit(0) # step cycle for step_i in input_step: n = int(step_i)*4+1 stepname = autostep[n] print("Step: ", stepname) # instance cycle for ins_i in input_instance: n = int(ins_i)*4+1 instancename = autoins[n] print("Instance: ", instancename) # access nodes & elements node = instance[instancename].nodes element = instance[instancename].elements n_nodes = len(node) n_elements = len(element) # access attribute(fieldOutputs) information frame = step[stepname].frames print('all frame',frame) # compute the number of element of each block p_elements = n_elements/1 + 1 lp_elements = n_elements - (p_elements*(1-1)) # last block # match nodes' label and its order in sequence (for empty nodes in tetra mesh) MLN = node[n_nodes-1].label TOTAL = [] # read node in sequence, and get the largest label of node(non-empty) # MLN is the max label of nodeset for i in node: TOTAL.append(i.label) if (i.label > MLN): MLN = i.label # match (the key) L = [] n = 0 for i in range(MLN): L.append(0) for i in TOTAL: L[i-1] = n n += 1 # frame cycle for i_frame in input_frame: # Detect whether the input frame is out of range try: odb.steps[stepname].frames[int(i_frame)] except: print("input frame exceeds the range of frames") os._exit(0) break # Access a frame N_Frame = odb.steps[stepname].frames[int(i_frame)] print("Frame:", i_frame) print("Partitionning model and writing vtk files ......") # piece cycle, to partion the model and create each piece for vtk files time1 = time.time() print("frame:", i_frame, ";") # Reorganization # Control&Storage # estimate whether the node has already existed stg_p = [] # store the reorganized node for element stg_e = [] # store the reorganized node for node stg_n = [] for i in range(MLN): stg_p.append(-1) nodecount = 0 # reorganize the node and element (reconstruct the mesh) M = range(0, n_elements) for i in M: for j in range(mesh_conner): k = element[i].connectivity[j] - 1 if (stg_p[k] < 0): stg_p[k] = nodecount stg_n.append(L[k]) stg_e.append(nodecount) nodecount += 1 else: stg_e.append(stg_p[k]) # compute point quantity n_reop = len(stg_n) reop_N = range(0, len(stg_n)) # create and open a VTK(.vtu) files outfile = open(os.path.join(vtk_path)+'_'+stepname + '_'+instancename+'f%03d' % int(i_frame)+'.vtu', 'w') # , including the type of mesh, version, and byte_order outfile.write( ''+'\n') # outfile.write(''+'\n') # , including the number of points and cells outfile.write(''+'\n') print("Writing Nodes ......") # Write nodes into vtk files outfile.write(''+'\n') outfile.write( ''+'\n') for i in reop_N: nt = stg_n[i] k = node[stg_n[i]].label-1 # base shape X, Y, Z = node[nt].coordinates[0], node[nt].coordinates[1], node[nt].coordinates[2] # modify shape # X,Y,Z = node[nt].coordinates[0]+ux,node[nt].coordinates[1]+uy,node[nt].coordinates[2]+uz outfile.write(' '+'%11.8e' % X+' '+'%11.8e' % Y+' '+'%11.8e' % Z+'\n') outfile.write(''+'\n') outfile.write(''+'\n') # print("Writing Results data ......") # Write results data into vtk files col = {"Scalars": [], "Vevtors": [], "Tensors": []} # 'U','A', 'V', 'RF','PEEQ','S' for var_id in ['NT11']: try: col["Scalars"].append("Temperature") except: print('jump', var_id) con = "Scalars="+'"'+','.join(col["Scalars"])+'"' # con = "Tensors="+'"'+','.join(col["Tensors"])+'"' + " "+ \ # "Vevtors="+'"'+','.join(col["Vevtors"])+'"' + " "+ \ # "Scalars="+'"'+','.join(col["Scalars"])+'"' outfile.write("<"+"PointData"+" "+con+">"+'\n') for var_id in ['NT11']: fieldOutputs = N_Frame.fieldOutputs[var_id] from utils_odb import NT11 as pq_class pq_class(fieldOutputs,outfile,reop_N) outfile.write(""+'\n') # print("Writing Cells ......") # Write cells into vtk files outfile.write(''+'\n') # Connectivity 8 node outfile.write( ''+'\n') if (mesh_type == 12): for i in range(len(stg_e)/8): outfile.write(str(stg_e[i*8])+' '+str(stg_e[i*8+1])+' '+str(stg_e[i*8+2])+' '+str(stg_e[i*8+3])+' '+str( stg_e[i*8+4])+' '+str(stg_e[i*8+5])+' '+str(stg_e[i*8+6])+' '+str(stg_e[i*8+7])+'\n') if (mesh_type == 10): for i in range(len(stg_e)/4): outfile.write(str( stg_e[i*4])+' '+str(stg_e[i*4+1])+' '+str(stg_e[i*4+2])+' '+str(stg_e[i*4+3])+'\n') outfile.write(''+'\n') # Offsets outfile.write( ''+'\n') for i in range(len(stg_e)/mesh_conner): outfile.write(str(i*mesh_conner+mesh_conner)+'\n') outfile.write(''+'\n') # Mesh Type outfile.write( ''+'\n') for i in range(len(stg_e)/mesh_conner): outfile.write(str(mesh_type)+'\n') outfile.write(''+'\n') outfile.write(''+'\n') # # outfile.write(''+'\n') # outfile.write(''+'\n') # outfile.write(''+'\n') outfile.close() print("Time elapsed: ", time.time() - time1, "s") odb.close() print("Total time elapsed: ", time.time() - starttime, "s") # get odb file's path odb_path = 'C:/Users/OPTX/Downloads/Digital-Twin/odb2vtk/Thermal.odb' # get the output files' path vtk_path = 'C:/Users/OPTX/Downloads/Digital-Twin/odb2vtk/' # not.vtu,.vtk # get the mesh type mesh_type = 12 # c3d8? mesh_conner = 0 if (mesh_type == 12): mesh_conner = 8 mesh_name = "Hexahedron" if (mesh_type == 10): mesh_conner = 4 mesh_name = "Tetra" if (mesh_conner == 0): print("Mesh type error or unidentified") os._exit(0) # get the frame input_frame = range(1, 4+1) # get the step input_step = '0'.split(",") # get the instance input_instance = '0'.split(",") # end reding and close odb2vtk file ConvertOdb2Vtk()