Source code for openglider.glider.in_out.export_3d

import math
import numpy

# from openglider.graphics import Graphics3D, Line
from openglider.vector.functions import norm, normalize
from openglider.utils.distribution import Distribution


[docs]def export_obj(glider, path, midribs=0, numpoints=None, floatnum=6, copy=True): other = glider.copy_complete() if copy else glider if numpoints: other.profile_numpoints = numpoints mesh = glider.get_mesh(midribs=midribs) mesh.export_obj(path)
[docs]def export_json(glider, path, numpoints, midribs=0, wake_panels=1, wake_length=0.2, *other): """ export json geometry file for panelmethod calculation """ class Node(): def __init__(self, p, n_id=None, is_wake=False): self.point = numpy.array(p) self.n_id = n_id self.is_wake = is_wake def __json__(self): return self.point.tolist() class Panel(): def __init__(self, nodes, p_id=None): self.nodes = nodes self.neighbours = [None, None, None, None] self.p_id = p_id @property def node_nos(self): return [node.n_id for node in self.nodes] @property def is_wake(self): return any([tha_node.is_wake for tha_node in self.nodes]) # This is just lazyness.. def get_neighbours(self, panel_list): self.neighbours = [self.get_neighbour(self.nodes[0], self.nodes[1], pan_list=panel_list), self.get_neighbour(self.nodes[1], self.nodes[2], pan_list=panel_list), self.get_neighbour(self.nodes[2], self.nodes[3], pan_list=panel_list), self.get_neighbour(self.nodes[3], self.nodes[0], pan_list=panel_list)] def get_neighbour(self, p1, p2, pan_list): for i, pan in enumerate(pan_list): if p1 in pan.nodes and p2 in pan.nodes and pan is not self: return i return None def neighbour_ids(self): get_id = lambda p: p.p_id if p else p return [get_id(n) for n in self.neighbours] def __json__(self): return {"is_wake": self.is_wake, "neighbours": self.neighbour_ids(), "nodes": self.node_nos} glide_alpha = numpy.arctan(glider.glide) glider = glider.copy_complete() glider.profile_numpoints = numpoints rib_len = len(glider.ribs[0].profile_2d) v_inf = numpy.array([numpy.sin(glide_alpha), 0, numpy.cos(glide_alpha)]) node_ribs = [[Node(node) for node in rib[1:]] for rib in glider.return_ribs(midribs)] nodes_flat = [] panel_ribs = [] panels = [] # Generate Wake for rib in node_ribs: rib += [ Node(rib[-1].point + v_inf * (i + 1) / wake_panels * wake_length, is_wake=True) for i in range(wake_panels)] # append to flat-list and >>calculate<< index for node in rib: node.n_id = len(nodes_flat) nodes_flat.append(node) # Generate Panels for left_rib, right_rib in zip(node_ribs[:-1], node_ribs[1:]): panel_rib = [] pan = Panel([left_rib[0], left_rib[-wake_panels - 1], right_rib[-wake_panels - 1], right_rib[0]], p_id=len(panels)) panel_rib.append(pan) panels.append(pan) for i in range(len(left_rib) - 1): pan = Panel([left_rib[i + 1], left_rib[i], right_rib[i], right_rib[i + 1]], p_id=len(panels)) panels.append(pan) panel_rib.append(pan) panel_ribs.append(panel_rib) for i, row in enumerate(panel_ribs): for j, panel in enumerate(row): # left neighbour if i > 0 and not panel.is_wake: panel.neighbours[0] = panel_ribs[i - 1][j] else: panel.neighbours[0] = None # panel.neighbours[1] = row[rib_len-j-1] # back neighbour if j > 0 and j < rib_len - 1: panel.neighbours[1] = row[j - 1] else: panel.neighbours[1] = row[rib_len - 2] # right neighbour if i < len(panel_ribs) - 1 and not panel.is_wake: panel.neighbours[2] = panel_ribs[i + 1][j] else: panel.neighbours[2] = None #panel.neighbours[3] = row[rib_len - j - 1] # front neighbour if not panel.is_wake: panel.neighbours[3] = row[j + 1] else: panel.neighbours[3] = row[0] print(panels[10].is_wake, panels[10].neighbours[1].is_wake, panels[10].neighbours[3].is_wake) # for pan in panels: # pan.get_neighbours(panels) # pan.node_nos = [nodes_flat.index if tha_node is not None else None for tha_node in pan.nodes] #import openglider.graphics as graph #graph.Graphics([graph.Polygon([n.n_id for n in panel.nodes], # colour=[255, 255*(1-panel.is_wake), 255]) # for panel in panels], # [n.point for n in nodes_flat]) return {'nodes': [node.__json__() for node in nodes_flat], 'panels': [panel.__json__() for panel in panels], 'config': {'v_inf': v_inf.tolist(), 'coefficient': 6., 'density': 1.2, 'pressure': 1.013, 'request_panels': True, 'request_nodes': True}}
[docs]def export_dxf(glider, path="", midribs=0, numpoints=None, *other): from dxfwrite import DXFEngine as dxf outfile = dxf.drawing(path) other = glider.copy_complete() if numpoints: other.profile_numpoints = numpoints ribs = other.return_ribs(midribs) panels = [] points = [] outfile.add_layer('RIBS', color=2) for rib in ribs: outfile.add(dxf.polyface(rib * 1000, layer='RIBS')) outfile.add(dxf.polyline(rib * 1000, layer='RIBS')) return outfile.save()
[docs]def export_apame(glider, path="", midribs=0, numpoints=None, *other): other = glider.copy_complete() if numpoints: other.profile_numpoints = numpoints ribs = other.return_ribs(midribs) v_inf = glider.lineset.v_inf speed = norm(v_inf) glide = numpy.arctan(v_inf[2]/v_inf[0]) # write config outfile = open(path, "w") outfile.write("APAME input file\nVERSION 3.0\n") outfile.write("AIRSPEED {}\n".format(speed)) outfile.write( "DENSITY 1.225\nPRESSURE 1.013e+005\nMACH 0\nCASE_NUM 1\n") # TODO: Multiple cases outfile.write(str(math.tan(1 / glide)) + "\n0\n") outfile.write("WINGSPAN " + str(other.span) + "\n") outfile.write("MAC 2") # TODO: Mean Choord outfile.write("SURFACE " + str(other.area) + "\n") outfile.write("ORIGIN\n0 0 0\n") outfile.write("METHOD 0\nERROR 1e-007\nCOLLDIST 1e-007\n") outfile.write("FARFIELD " + str(5) + "\n") # TODO: farfield argument outfile.write( "COLLCALC 0\nVELORDER 2\nRESULTS 1\n1 1 1 1 1 1 1 1 1 1 1 1 1\n\n") outfile.write("NODES " + str(len(ribs) * len(ribs[0])) + "\n") for rib in ribs: for point in rib: for coord in point: outfile.write(str(coord) + "\t") outfile.write("\n") outfile.write("\nPANELS " + str((len(ribs) - 1) * ( len(ribs[0]) - 1)) + "\n") # TODO: ADD WAKE + Neighbours! for i in range(len(ribs) - 1): for j in range(other.profile_numpoints): # COUNTER-CLOCKWISE! outfile.write("1 {0!s}\t{1!s}\t{2!s}\t{3!s}\n".format( i * len(ribs[0]) + j + 1, (i + 1) * len(ribs[0]) + j + 1, (i + 1) * len(ribs[0]) + j + 2, i * len(ribs[0]) + j + 2)) return outfile.close()
[docs]def paraBEM_Panels(glider, midribs=0, profile_numpoints=None, num_average=0, symmetric=False, distribution=None): """return the vertices, panels and the trailing edge of a glider, as paraBEM objects. midribs: midribs of a cell spanwise. if num_average is greater then 0 ballooning will be disables profile_numpoints: coordinates of every rib, choordwise num_average: steps to average a cell profile symmetric: set to True if a symmetric result is expected (this will reduce evaluation time) """ # paraBEM is not a dependency of openglider so if problems occure here, get the module. import paraBEM if symmetric: glider = glider.copy() else: glider = glider.copy_complete() glider.close_rib(0) glider.close_rib() if profile_numpoints: glider.profile_x_values = Distribution.from_nose_cos_distribution(profile_numpoints, 0.2) if num_average > 0: ribs = glider.return_average_ribs(midribs, num_average) else: ribs = glider.return_ribs(midribs) # deleting the last vertex of every rib (no trailing edge gap) ribs = [rib[:-1] for rib in ribs] # get a numbered representation + flatten vertices i = 0 vertices = [] ribs_new = [] panels = [] sym_panels = [] trailing_edge = [] for rib in ribs: rib_new = [] for vertex in rib: rib_new.append(i) vertices.append(vertex) i += 1 rib_new.append(rib_new[0]) ribs_new.append(rib_new) ribs = ribs_new panel_nr = 0 for i, rib_i in enumerate(ribs[:-1]): rib_j = ribs[i+1] if symmetric: if vertices[rib_j[0]][1] > 0.00001: trailing_edge.append(rib_i[0]) else: trailing_edge.append(rib_i[0]) if i == len(ribs[:-2]): trailing_edge.append(rib_j[0]) for k, _ in enumerate(rib_j[:-1]): l = k + 1 panel = [rib_i[k], rib_j[k], rib_j[l], rib_i[l]] if symmetric: sym = True add_panel = False for p in panel: if not vertices[p][1] > -0.000001: # if one point lies on the y- side sym = False # y- is the mirrored side if not vertices[p][1] < 0.0001: # if one point lies on the y+ side add_panel = True if add_panel: panels.append(panel) if sym: sym_panels.append(panel_nr) panel_nr += 1 else: panels.append(panel) vertices = [paraBEM.PanelVector3(*point) for point in vertices] panels = [paraBEM.Panel3([vertices[nr] for nr in panel]) for panel in panels] trailing_edge = [vertices[nr] for nr in trailing_edge] for nr in sym_panels: panels[nr].set_symmetric() return vertices, panels, trailing_edge