def writeVSPFile(self, fileName, exportSet=0): """Take the current design and write a new FSP file""" vsp.WriteVSPFile(fileName, exportSet)
def write(vehicle, tag, fuel_tank_set_ind=3, verbose=True, write_file=True, OML_set_ind = 4, write_igs = False): """This writes a SUAVE vehicle to OpenVSP format. It will take wing segments into account if they are specified in the vehicle setup file. Assumptions: Vehicle is composed of conventional shape fuselages, wings, and propulsors. Any propulsor that should be created is tagged as 'turbofan'. Source: N/A Inputs: vehicle. tag [-] wings.*. (* is all keys) origin [m] in all three dimensions spans.projected [m] chords.root [m] chords.tip [m] sweeps.quarter_chord [radians] twists.root [radians] twists.tip [radians] thickness_to_chord [-] dihedral [radians] tag <string> Segments.*. (optional) twist [radians] percent_span_location [-] .1 is 10% root_chord_percent [-] .1 is 10% dihedral_outboard [radians] sweeps.quarter_chord [radians] thickness_to_chord [-] propulsors.turbofan. (optional) number_of_engines [-] engine_length [m] nacelle_diameter [m] origin [m] in all three dimension, should have as many origins as engines OpenVSP_simple (optional) <boolean> if False (default) create a flow through nacelle, if True creates a roughly biparabolic shape fuselages.fuselage (optional) width [m] lengths.total [m] heights. maximum [m] at_quarter_length [m] at_wing_root_quarter_chord [m] at_three_quarters_length [m] effective_diameter [m] fineness.nose [-] ratio of nose section length to fuselage width fineness.tail [-] ratio of tail section length to fuselage width tag <string> OpenVSP_values. (optional) nose.top.angle [degrees] nose.top.strength [-] this determines how much the specified angle influences that shape nose.side.angle [degrees] nose.side.strength [-] nose.TB_Sym <boolean> determines if top angle is mirrored on bottom nose.z_pos [-] z position of the nose as a percentage of fuselage length (.1 is 10%) tail.top.angle [degrees] tail.top.strength [-] tail.z_pos (optional, 0.02 default) [-] z position of the tail as a percentage of fuselage length (.1 is 10%) fuel_tank_set_index <int> OpenVSP object set containing the fuel tanks Outputs: <tag>.vsp3 This is the OpenVSP representation of the aircraft Properties Used: N/A """ # Reset OpenVSP to avoid including a previous vehicle if verbose: print('Reseting OpenVSP Model in Memory') try: vsp.ClearVSPModel() except NameError: print('VSP import failed') return -1 area_tags = dict() # for wetted area assignment # ------------- # Wings # ------------- # Default Set_0 in OpenVSP is index 3 vsp.SetSetName(fuel_tank_set_ind, 'fuel_tanks') vsp.SetSetName(OML_set_ind, 'OML') for wing in vehicle.wings: if verbose: print('Writing '+wing.tag+' to OpenVSP Model') area_tags, wing_id = write_vsp_wing(wing,area_tags, fuel_tank_set_ind, OML_set_ind) if wing.tag == 'main_wing': main_wing_id = wing_id # ------------- # Engines # ------------- ## Skeleton code for props and pylons can be found in previous commits (~Dec 2016) if desired ## This was a place to start and may not still be functional if 'turbofan' in vehicle.propulsors: if verbose: print('Writing '+vehicle.propulsors.turbofan.tag+' to OpenVSP Model') turbofan = vehicle.propulsors.turbofan write_vsp_turbofan(turbofan, OML_set_ind) if 'turbojet' in vehicle.propulsors: turbofan = vehicle.propulsors.turbojet write_vsp_turbofan(turbofan, OML_set_ind) # ------------- # Fuselage # ------------- for key, fuselage in vehicle.fuselages.items(): if verbose: print('Writing '+fuselage.tag+' to OpenVSP Model') try: area_tags = write_vsp_fuselage(fuselage, area_tags, vehicle.wings.main_wing, fuel_tank_set_ind, OML_set_ind) except AttributeError: area_tags = write_vsp_fuselage(fuselage, area_tags, None, fuel_tank_set_ind, OML_set_ind) vsp.Update() # Write the vehicle to the file if write_file ==True: cwd = os.getcwd() filename = tag + ".vsp3" if verbose: print('Saving OpenVSP File at '+ cwd + '/' + filename) vsp.WriteVSPFile(filename) elif verbose: print('Not Saving OpenVSP File') if write_igs: if verbose: print('Exporting IGS File') vehicle_id = vsp.FindContainersWithName('Vehicle')[0] parm_id = vsp.FindParm(vehicle_id,'LabelID','IGESSettings') vsp.SetParmVal(parm_id, 0.) vsp.ExportFile(tag + ".igs", OML_set_ind, vsp.EXPORT_IGES) return area_tags
# Copy Pod Geom vsp.CopyGeomToClipboard(pod_id) vsp.PasteGeomClipboard(fuse_id) # make fuse parent # Set Name vsp.SetGeomName(pod_id, "Original_Pod") second_pod_id = vsp.FindGeom("Pod", 0) # Change Location and Symmetry vsp.SetParmVal(second_pod_id, "Sym_Planar_Flag", "Sym", 0) vsp.SetParmVal(second_pod_id, "Y_Location", "XForm", 0.0) vsp.SetParmVal(second_pod_id, "Z_Location", "XForm", 1.0) fname = "apitest1.vsp3" vsp.WriteVSPFile(fname) geoms = vsp.FindGeoms() print("All geoms in Vehicle.") print(geoms) errorMgr.PopErrorAndPrint(stdout) # ==== Use Case 2 ====# vsp.VSPRenew() errorMgr.PopErrorAndPrint(stdout) geoms = vsp.FindGeoms()
def write_vsp_mesh(geometry, tag, half_mesh_flag, growth_ratio, growth_limiting_flag): """This create an .stl surface mesh based on a vehicle stored in a .vsp3 file. Assumptions: None Source: N/A Inputs: geometry. - Also passed to set_sources wings.main_wing.chords.mean_aerodynamic [m] half_mesh_flag <boolean> determines if a symmetry plane is created growth_ratio [-] growth ratio for the mesh growth_limiting_flag <boolean> determines if 3D growth limiting is used Outputs: <tag>.stl Properties Used: N/A """ # Reset OpenVSP to avoid including a previous vehicle vsp.ClearVSPModel() if 'turbofan' in geometry.networks: print( 'Warning: no meshing sources are currently implemented for the nacelle' ) # Turn on symmetry plane splitting to improve robustness of meshing process if half_mesh_flag == True: f = fileinput.input(tag + '.vsp3', inplace=1) for line in f: if 'SymmetrySplitting' in line: print(line[0:34] + '1' + line[35:-1]) else: print(line) vsp.ReadVSPFile(tag + '.vsp3') # Set output file types and what will be meshed file_type = vsp.CFD_STL_TYPE + vsp.CFD_KEY_TYPE set_int = vsp.SET_ALL vsp.SetComputationFileName(vsp.CFD_STL_TYPE, tag + '.stl') vsp.SetComputationFileName(vsp.CFD_KEY_TYPE, tag + '.key') # Set to create a tagged STL mesh file vehicle_cont = vsp.FindContainer('Vehicle', 0) STL_multi = vsp.FindParm(vehicle_cont, 'MultiSolid', 'STLSettings') vsp.SetParmVal(STL_multi, 1.0) vsp.SetCFDMeshVal(vsp.CFD_FAR_FIELD_FLAG, 1) if half_mesh_flag == True: vsp.SetCFDMeshVal(vsp.CFD_HALF_MESH_FLAG, 1) # Figure out the size of the bounding box vehicle_id = vsp.FindContainersWithName('Vehicle')[0] xlen = vsp.GetParmVal(vsp.FindParm(vehicle_id, "X_Len", "BBox")) ylen = vsp.GetParmVal(vsp.FindParm(vehicle_id, "Y_Len", "BBox")) zlen = vsp.GetParmVal(vsp.FindParm(vehicle_id, "Z_Len", "BBox")) # Max length max_len = np.max([xlen, ylen, zlen]) far_length = 10. * max_len vsp.SetCFDMeshVal(vsp.CFD_FAR_SIZE_ABS_FLAG, 1) vsp.SetCFDMeshVal(vsp.CFD_FAR_LENGTH, far_length) vsp.SetCFDMeshVal(vsp.CFD_FAR_WIDTH, far_length) vsp.SetCFDMeshVal(vsp.CFD_FAR_HEIGHT, far_length) vsp.SetCFDMeshVal(vsp.CFD_FAR_MAX_EDGE_LEN, max_len) vsp.SetCFDMeshVal(vsp.CFD_GROWTH_RATIO, growth_ratio) if growth_limiting_flag == True: vsp.SetCFDMeshVal(vsp.CFD_LIMIT_GROWTH_FLAG, 1.0) # Set the max edge length so we have on average 50 elements per chord length MAC = geometry.wings.main_wing.chords.mean_aerodynamic min_len = MAC / 50. vsp.SetCFDMeshVal(vsp.CFD_MAX_EDGE_LEN, min_len) # vsp.AddDefaultSources() set_sources(geometry) vsp.Update() vsp.WriteVSPFile(tag + '_premesh.vsp3') print('Starting mesh for ' + tag + ' (This may take several minutes)') ti = time.time() vsp.ComputeCFDMesh(set_int, file_type) tf = time.time() dt = tf - ti print('VSP meshing for ' + tag + ' completed in ' + str(dt) + ' s')