def closest_point_on_line(a, b, c):
    """Closest point on line.
    Same as projection.

    Parameters
    ----------
    a: list
        First line point coordinates.
    b: list
        Second line point coordinates.
    c: list
        Point coordinates.

    Returns
    -------
    tuple
        The projected point coordinates and the distance from the input point.
    """

    ab = subtract_vectors(b, a)
    ac = subtract_vectors(c, a)

    if length_vector(ab) == 0:
        return a, distance_point_point(c, a)

    p = add_vectors(
        a, scale_vector(ab,
                        dot_vectors(ab, ac) / length_vector(ab)**2))
    distance = distance_point_point(c, p)
    return p, distance
Beispiel #2
0
 def DrawForeground(self, e):
     draw_dot = e.Display.DrawDot
     draw_arrows = e.Display.DrawArrows
     a = self.mouse.p1
     b = self.mouse.p2
     ab = subtract_vectors(b, a)
     Lab = length_vector(ab)
     if not Lab:
         return
     for index, vertex in enumerate(self.force_vertex_xyz):
         c = self.force_vertex_xyz[vertex]
         D = length_vector(
             cross_vectors(subtract_vectors(a, c), subtract_vectors(b, c)))
         if D / Lab < self.tol:
             point = Point3d(*c)
             draw_dot(point, str(index), self.dotcolor, self.textcolor)
             lines = List[Line](len(self.force_vertex_edges[vertex]))
             for u, v in self.force_vertex_edges[vertex]:
                 lines.Add(
                     Line(Point3d(*self.force_vertex_xyz[u]),
                          Point3d(*self.force_vertex_xyz[v])))
             draw_arrows(lines, self.linecolor)
             lines = List[Line](len(self.form_face_edges[vertex]))
             for u, v in self.form_face_edges[vertex]:
                 lines.Add(
                     Line(Point3d(*self.form_vertex_xyz[u]),
                          Point3d(*self.form_vertex_xyz[v])))
             draw_arrows(lines, self.linecolor)
             break
Beispiel #3
0
    def _tributary_areas(self, xyz):
        mesh = self.mesh
        key_index = self.key_index
        fkey_index = self.fkey_index
        is_loaded = self.is_loaded

        C = self.F.dot(xyz)

        areas = zeros((xyz.shape[0], 1))
        for u in mesh.vertices():
            p0 = xyz[key_index[u]]

            a = 0
            for v in mesh.halfedge[u]:
                p1 = xyz[key_index[v]]
                p01 = p1 - p0

                fkey = mesh.halfedge[u][v]
                if fkey is not None and is_loaded[fkey]:
                    p2 = C[fkey_index[fkey]]
                    a += 0.25 * length_vector(cross_vectors(p01, p2 - p0))

                fkey = mesh.halfedge[v][u]
                if fkey is not None and is_loaded[fkey]:
                    p3 = C[fkey_index[fkey]]
                    a += 0.25 * length_vector(cross_vectors(p01, p3 - p0))

            areas[key_index[u]] = a

        return areas
Beispiel #4
0
    def vertex_area(self, key):
        """Compute the tributary area of a vertex.

        Parameters
        ----------
        key : int
            The identifier of the vertex.

        Returns
        -------
        float
            The tributary are.

        """
        area = 0.

        p0 = self.vertex_coordinates(key)

        for nbr in self.halfedge[key]:
            p1 = self.vertex_coordinates(nbr)
            v1 = subtract_vectors(p1, p0)

            fkey = self.halfedge[key][nbr]
            if fkey is not None:
                p2 = self.face_centroid(fkey)
                v2 = subtract_vectors(p2, p0)
                area += length_vector(cross_vectors(v1, v2))

            fkey = self.halfedge[nbr][key]
            if fkey is not None:
                p3 = self.face_centroid(fkey)
                v3 = subtract_vectors(p3, p0)
                area += length_vector(cross_vectors(v1, v3))

        return 0.25 * area
Beispiel #5
0
    def DrawForeground(self, e):
        p1 = self.mouse.p1
        p2 = self.mouse.p2
        v12 = subtract_vectors(p2, p1)
        l12 = length_vector(v12)

        # force diagram
        for ckey in self.volmesh.cell:
            p0 = self.volmesh.cell_center(ckey)
            v01 = subtract_vectors(p1, p0)
            v02 = subtract_vectors(p2, p0)
            l = length_vector(cross_vectors(v01, v02))
            color = self.edgecolor
            if self.color_dict:
                color = FromArgb(*self.color_dict[ckey])
            if l12 == 0.0 or (l / l12) < self.tol:
                for hfkey in self.volmesh.cell_halffaces(ckey):
                    vkeys = self.volmesh.halfface_vertices(hfkey)
                    face_coordinates = [
                        self.volmesh.vertex_coordinates(vkey) for vkey in vkeys
                    ]
                    face_coordinates.append(face_coordinates[0])
                    polygon_xyz = [Point3d(*xyz) for xyz in face_coordinates]
                    e.Display.DrawPolyline(polygon_xyz, color, 3)
                break
Beispiel #6
0
    def calculate_selfweight(xyz):
        fkey_centroid = {
            fkey: mesh.face_centroid(fkey)
            for fkey in mesh.faces()
        }

        for u in mesh.vertices():
            i = key_index[u]
            p0 = xyz[i]
            a = 0

            for v in mesh.halfedge[u]:
                j = key_index[v]
                p1 = xyz[j]
                p01 = [p1[axis] - p0[axis] for axis in range(3)]

                fkey = mesh.halfedge[u][v]
                if fkey in fkey_centroid:
                    p2 = fkey_centroid[fkey]
                    p02 = [p2[axis] - p0[axis] for axis in range(3)]
                    a += 0.25 * length_vector(cross_vectors(p01, p02))

                fkey = mesh.halfedge[v][u]
                if fkey in fkey_centroid:
                    p3 = fkey_centroid[fkey]
                    p03 = [p3[axis] - p0[axis] for axis in range(3)]
                    a += 0.25 * length_vector(cross_vectors(p01, p03))

            sw[i] = a * ro[i]

        return sw
def closest_point_on_segment(a, b, c):
    """Closest point on segment.
    Different from projection because an extremity is yielded if the projection is on the line but outside the segment.

    Parameters
    ----------
    a: list
        First line point coordinates.
    b: list
        Second line point coordinates.
    c: list
        Point coordinates.

    Returns
    -------
    tuple
        The projected point coordinates and the distance from the input point.
    """

    p, distance = closest_point_on_line(a, b, c)

    ab = subtract_vectors(b, a)
    ap = subtract_vectors(p, a)

    if dot_vectors(ab, ap) < 0:
        return a, distance_point_point(c, a)
    elif length_vector(ab) < length_vector(ap):
        return b, distance_point_point(c, b)
    else:
        return p, distance
Beispiel #8
0
def plot_reaction_forces(structure, step, layer=None, scale=1.0):
    """ Plots reaction forces for the Structure analysis results.

    Parameters
    ----------
    structure : obj
        Structure object.
    step : str
        Name of the Step.
    layer : str
        Layer name for plotting.
    scale : float
        Scale of the arrows.

    Returns
    -------
    None

    """

    if not layer:
        layer = '{0}-{1}'.format(step, 'reactions')

    rs.CurrentLayer(rs.AddLayer(layer))
    rs.DeleteObjects(rs.ObjectsByLayer(layer))
    rs.EnableRedraw(False)

    rfx = structure.results[step]['nodal']['rfx']
    rfy = structure.results[step]['nodal']['rfy']
    rfz = structure.results[step]['nodal']['rfz']

    nkeys = rfx.keys()
    v = [scale_vector([rfx[i], rfy[i], rfz[i]], -scale * 0.001) for i in nkeys]
    rm = [length_vector(i) for i in v]
    rmax = max(rm)
    nodes = structure.nodes_xyz(nkeys)

    for i in nkeys:

        if rm[i] > 0.001:
            l = rs.AddLine(nodes[i], add_vectors(nodes[i], v[i]))
            rs.CurveArrows(l, 1)
            col = [
                int(j) for j in colorbar(rm[i] / rmax, input='float', type=255)
            ]
            rs.ObjectColor(l, col)
            vector = [rfx[i], rfy[i], rfz[i]]
            name = json.dumps({
                'rfx': rfx[i],
                'rfy': rfy[i],
                'rfz': rfz[i],
                'rfm': length_vector(vector)
            })
            rs.ObjectName(l, '_' + name)

    rs.CurrentLayer(rs.AddLayer('Default'))
    rs.LayerVisible(layer, False)
    rs.EnableRedraw(True)
Beispiel #9
0
    def DrawForeground(self, e):
        p1 = self.mouse.p1
        p2 = self.mouse.p2
        v12 = subtract_vectors(p2, p1)
        l12 = length_vector(v12)

        # force diagram

        for ckey in self.volmesh.cell:
            p0 = self.volmesh.cell_center(ckey)
            dual_p0 = self.network.vertex_coordinates(ckey)
            v01 = subtract_vectors(p1, p0)
            v02 = subtract_vectors(p2, p0)
            l = length_vector(cross_vectors(v01, v02))

            if l12 == 0.0 or (l / l12) < self.tol:

                hf_colors = {}

                nbr_vkeys = self.network.vertex_neighbours(ckey)

                for index, nbr_vkey in enumerate(nbr_vkeys):
                    value = float(index) / (len(nbr_vkeys) - 1)

                    print('boo', value)

                    color = i_to_rgb(value)
                    color = System.Drawing.Color.FromArgb(*color)
                    nbr_xyz = self.network.vertex_coordinates(nbr_vkey)
                    e.Display.DrawLine(Point3d(*dual_p0), Point3d(*nbr_xyz),
                                       color, 4)

                    hfkey = self.volmesh.cell_pair_halffaces(ckey, nbr_vkey)[0]
                    hf_colors[hfkey] = color

                for hfkey in self.volmesh.cell_halffaces(ckey):
                    vkeys = self.volmesh.halfface_vertices(hfkey)
                    face_coordinates = [
                        self.volmesh.vertex_coordinates(vkey) for vkey in vkeys
                    ]
                    face_coordinates.append(face_coordinates[0])
                    polygon_xyz = [Point3d(*xyz) for xyz in face_coordinates]
                    e.Display.DrawDot(Point3d(*p0), str(ckey), self.dotcolor,
                                      self.textcolor)
                    e.Display.DrawPolyline(polygon_xyz, self.edgecolor, 2)

                    e.Display.DrawDot(Point3d(*dual_p0), str(ckey),
                                      self.dotcolor, self.textcolor)

                    if hfkey in hf_colors:
                        hf_color = hf_colors[hfkey]
                        e.Display.DrawPolygon(polygon_xyz,
                                              hf_color,
                                              filled=True)

                break
Beispiel #10
0
class LoadUpdater(object):
    """"""
    def __init__(self, mesh, p0, thickness=1.0, density=1.0, live=0.0):
        self.mesh       = mesh
        self.p0         = p0
        self.thickness  = thickness
        self.density    = density
        self.live       = live
        self.key_index  = mesh.key_index()
        self.fkey_index = {fkey: index for index, fkey in enumerate(mesh.faces())}
        self.is_loaded  = {fkey: mesh.get_face_attribute(fkey, 'is_loaded') for fkey in mesh.faces()}
        self.F          = self.face_matrix()
        
    def __call__(self, p, xyz):
        ta = self._tributary_areas(xyz)
        sw = ta * self.thickness * self.density + ta * self.live
        p[:, 2] = self.p0[:, 2] + sw[:, 0]


    def face_matrix(self):
        face_vertices = [None] * self.mesh.number_of_faces()
        for fkey in self.mesh.fes():
            face_vertices[self.fkey_index[fkey]] = [self.key_index[key] for key in self.mesh.face_vertices(fkey)]
        return face_matrix(face_vertices, rtype='csr', normalize=True)

    def _tributary_areas(self, xyz):ac
        mesh       = self.mesh
        key_index  = self.key_index
        fkey_index = self.fkey_index
        is_loaded  = self.is_loaded

        C = self.F.dot(xyz)

        areas = zeros((xyz.shape[0], 1))
        for u in mesh.vertices():
            p0 = xyz[key_index[u]]

            a = 0
            for v in mesh.halfedge[u]:
                p1  = xyz[key_index[v]]
                p01 = p1 - p0

                fkey = mesh.halfedge[u][v]
                if fkey is not None and is_loaded[fkey]:
                    p2 = C[fkey_index[fkey]]
                    a += 0.25 * length_vector(cross_vectors(p01, p2 - p0))

                fkey = mesh.halfedge[v][u]
                if fkey is not None and is_loaded[fkey]:
                    p3 = C[fkey_index[fkey]]
                    a += 0.25 * length_vector(cross_vectors(p01, p3 - p0))

            areas[key_index[u]] = a

        return areas
Beispiel #11
0
 def intersect(self):
     intersections = []
     for u, v in list(self.mesh.edges()):
         a = self.mesh.vertex_attributes(u, 'xyz')
         b = self.mesh.vertex_attributes(v, 'xyz')
         x = intersection_segment_plane((a, b), self.plane)
         if not x:
             continue
         L_ax = length_vector(subtract_vectors(x, a))
         L_ab = length_vector(subtract_vectors(b, a))
         t = L_ax / L_ab
         key = self.mesh.split_edge(u, v, t=t, allow_boundary=True)
         intersections.append(key)
     self._intersections = intersections
Beispiel #12
0
 def DrawForeground(self, e):
     p1 = self.mouse.p1
     p2 = self.mouse.p2
     v12 = subtract_vectors(p2, p1)
     l12 = length_vector(v12)
     for index, (key, attr) in enumerate(self.mesh.vertices(True)):
         p0 = attr['x'], attr['y'], attr['z']
         text = str(index)
         v01 = subtract_vectors(p1, p0)
         v02 = subtract_vectors(p2, p0)
         l = length_vector(cross_vectors(v01, v02))  # noqa: E741
         if l12 == 0.0 or (l / l12) < self.tol:
             point = Point3d(*p0)
             e.Display.DrawDot(point, text, self.dotcolor, self.textcolor)
             break
Beispiel #13
0
def matrix_from_axis_angle_vector(axis_angle_vector, point=[0, 0, 0]):
    """Calculates a rotation matrix from an axis-angle vector.

    Parameters
    ----------
    axis_angle_vector : [float, float, float]
        Three numbers that represent the axis of rotation and angle of rotation
        through the vector's magnitude.
    point : [float, float, float] | :class:`compas.geometry.Point`, optional
        A point to perform a rotation around an origin other than [0, 0, 0].

    Returns
    -------
    list[list[float]]
        The 4x4 transformation matrix representing a rotation.

    Examples
    --------
    >>> aav1 = [-0.043, -0.254, 0.617]
    >>> R = matrix_from_axis_angle_vector(aav1)
    >>> aav2 = axis_angle_vector_from_matrix(R)
    >>> allclose(aav1, aav2)
    True

    """
    axis = list(axis_angle_vector)
    angle = length_vector(axis_angle_vector)
    return matrix_from_axis_and_angle(axis, angle, point)
Beispiel #14
0
    def draw_vector_field(self, field, color, uniform, scale, width=0.5):
        """
        Draws a vector field on a mesh.

        It assumes the field and the mesh faces have the same keys.
        """
        _lines = []
        lines = []
        mesh = self.mesh

        for fkey in range(field.size()):
            vector = field[fkey]
            length = scale
            if not uniform:
                length = length_vector(vector) * scale
            _lines.append(line_sdl(mesh.face_centroid(fkey), vector, length))

        _lines = [line for line in map(line_tuple_to_dict, _lines)]

        for line in _lines:
            line["width"] = width
            line["color"] = color

        lines.extend(_lines)

        self.draw_lines(lines)
 def from_axis_angle_vector(cls, axis_angle_vector):
     """Create rotation matrix from axis-angle representation as vector.
     """ 
     
     axis_angle_vector = list(axis_angle_vector)
     angle = length_vector(axis_angle_vector)
     return cls.from_axis_and_angle(axis_angle_vector, angle)
Beispiel #16
0
def test_volume_polyhedron(polyhedron, volume):
    if volume is None:
        L = length_vector(subtract_vectors(
            polyhedron.vertices[0], polyhedron.vertices[1]))
        volume = L * L * L
    V = volume_polyhedron(polyhedron)
    assert V == pytest.approx(volume, 0.001)
Beispiel #17
0
def test_volume_polyhedron(polyhedron, volume):
    if volume is None:
        L = length_vector(
            subtract_vectors(polyhedron.vertices[0], polyhedron.vertices[1]))
        volume = L * L * L
    V = volume_polyhedron(polyhedron)
    assert close(V, volume)
Beispiel #18
0
def smooth_network_length(network, lmin, lmax, fixed=None, kmax=1, d=0.5, callback=None, callback_args=None):
    fixed = fixed or []
    fixed = set(fixed)

    if callback:
        if not callable(callback):
            raise Exception('The callback is not callable.')

    for k in range(kmax):
        key_xyz = {key: network.vertex_coordinates(key) for key in network.vertices()}

        for key in network:
            if key in fixed:
                continue

            ep = key_xyz[key]
            points = []

            for nbr in network.vertex_neighbours(key):
                sp    = key_xyz[nbr]
                vec   = subtract_vectors(ep, sp)
                lvec  = length_vector(vec)
                scale = max(lmin, min(lvec, lmax))
                p     = add_vectors(sp, scale_vector(vec, scale / lvec))
                points.append(p)

            x, y, z = centroid_points(points)

            attr = network.vertex[key]
            attr['x'] += d * (x - ep[0])
            attr['y'] += d * (y - ep[1])
            attr['z'] += d * (z - ep[2])

        if callback:
            callback(network, k, callback_args)
Beispiel #19
0
def get_modal_shapes_from_result_files(out_path):
    modal_path = out_path + '/modal_out/'
    try:
        files = os.listdir(modal_path)
    except (Exception):
        print('Result files not found')
        return None, None
    filenames = []
    for f in files:
        if f.startswith("modal_shape_"):
            filenames.append(f)
    modal_files = []
    for i in range(len(filenames)):
        f = 'modal_shape_' + str(i + 1) + '.txt'
        modal_files.append(open(modal_path + '/' + f, 'r'))

    modes_dict = {}
    for i, f in enumerate(modal_files):
        modes_dict['ux' + str(i)] = {}
        modes_dict['uy' + str(i)] = {}
        modes_dict['uz' + str(i)] = {}
        modes_dict['um' + str(i)] = {}
        mode = f.readlines()
        for j in range(len(mode)):
            string = mode[j].split(',')
            a = map(float, string)
            nkey = int(a[0]) - 1
            modes_dict['ux' + str(i)][nkey] = a[1]
            modes_dict['uy' + str(i)][nkey] = a[2]
            modes_dict['uz' + str(i)][nkey] = a[3]
            modes_dict['um' + str(i)][nkey] = length_vector((a[1], a[2], a[3]))
        f.close()

    return modes_dict
Beispiel #20
0
    def from_axis_angle_vector(cls, axis_angle_vector, point=[0, 0, 0]):
        """Construct a rotation transformation from an axis-angle vector.

        Parameters
        ----------
        axis_angle_vector : [float, float, float] | :class:`compas.geometry.Vector`
            Three numbers that represent the axis of rotation and angle of rotation through the vector's magnitude.
        point : [float, float, float] | :class:`compas.geometry.Point`, optional
            A point to perform a rotation around an origin other than [0, 0, 0].

        Returns
        -------
        :class:`compas.geometry.Rotation`

        Examples
        --------
        >>> from compas.geometry import allclose
        >>> aav1 = [-0.043, -0.254, 0.617]
        >>> R = Rotation.from_axis_angle_vector(aav1)
        >>> aav2 = R.axis_angle_vector
        >>> allclose(aav1, aav2)
        True

        """
        angle = length_vector(axis_angle_vector)
        return cls.from_axis_and_angle(axis_angle_vector, angle, point)
Beispiel #21
0
def polygon_area_footprint(polygon):
    """Compute the non-oriented area of a polygon (can be convex or concave).

    Parameters
    ----------
    polygon : list of lists
        A list of polygon point coordinates.

    Returns
    -------
    float
        The non-oriented area of the polygon.

    """
    area = 0
    w    = centroid_points(polygon)

    for i in range(-1, len(polygon) - 1):
        u      = polygon[i]
        v      = polygon[i + 1]
        uv     = subtract_vectors(v, u)
        vw     = subtract_vectors(w, v)
        normal = scale_vector(cross_vectors(uv, vw), 0.5)
        area   += length_vector(normal)

    return area
Beispiel #22
0
def trimesh_edge_cotangent(mesh, u, v):
    """Compute the cotangent of the angle opposite a halfedge of the triangle mesh.

    Parameters
    ----------
    mesh : compas.datastructures.Mesh
        The triangle mesh data structure.
    u : int
        The identifier of the first vertex of the halfedge.
    v : int
        The identifier of the second vertex of the halfedge.

    Returns
    -------
    float
        The edge cotangent.

    Examples
    --------
    .. code-block:: python

        pass

    """
    fkey = mesh.halfedge[u][v]
    cotangent = 0.0
    if fkey is not None:
        w = mesh.face_vertex_ancestor(fkey, u)
        wu = mesh.edge_vector(w, u)
        wv = mesh.edge_vector(w, v)
        l = length_vector(cross_vectors(wu, wv))
        if l:
            cotangent = dot_vectors(wu, wv) / l
    return cotangent
Beispiel #23
0
def trimesh_edge_cotangent(mesh, u, v):
    """Compute the cotangent of the angle opposite a halfedge of the triangle mesh.

    Parameters
    ----------
    mesh : :class:`compas.datastructures.Mesh`
        Instance of mesh.
    u : int
        The identifier of the first vertex of the halfedge.
    v : int
        The identifier of the second vertex of the halfedge.

    Returns
    -------
    float
        The edge cotangent.

    """
    fkey = mesh.halfedge[u][v]
    cotangent = 0.0
    if fkey is not None:
        w = mesh.face_vertex_ancestor(fkey, u)
        wu = mesh.edge_vector(w, u)
        wv = mesh.edge_vector(w, v)
        length = length_vector(cross_vectors(wu, wv))
        if length:
            cotangent = dot_vectors(wu, wv) / length
    return cotangent
def GetConvexPolygonArea(polygon):

    center = [0.0,0.0,0.0]


    for p in polygon:
        center=[center[0]+p[0],center[1]+p[1],center[2]+p[2]]
   
    n = len(polygon.points)
    center=[center[0]/n,center[1]/n,center[2]/n]

    areaSum = 0.0



    for i in range(0, n):
        
        p0 = polygon[i]
        p1 = polygon[(i+1)%n]
        p2 = center
        u = subtract_vectors(p2,p1)
        v = subtract_vectors(p2,p0)
        area = length_vector(cross_vectors(u,v))*0.5
        areaSum+=area

    

    print(areaSum)

    return areaSum
def vector_lines_on_faces(mesh, vector_tag, uniform=True, factor=0.02):
    '''
    '''
    def line_sdl(start, direction, length):
        direction = normalize_vector(direction[:])
        a = add_vectors(start, scale_vector(direction, -length))
        b = add_vectors(start, scale_vector(direction, +length))

        return a, b

    lines = []
    for fkey, attr in mesh.faces(data=True):
        vector = attr.get(vector_tag)

        if not vector:
            raise ValueError('Vector {} not defined on face {}'.format(
                vector_tag, fkey))

        if uniform:
            vec_length = factor
        else:
            vec_length = length_vector(vector) * factor

        pt = mesh.face_centroid(fkey)
        lines.append(line_sdl(pt, vector, vec_length))
    return lines
Beispiel #26
0
def get_reactions_from_result_files(out_path, step):
    filename = step + '_reactions.txt'
    try:
        rfile   = open(os.path.join(out_path, filename), 'r')
    except(Exception):
        return None
    r = rfile.readlines()
    # react_dict = {}
    # for i in range(len(r)):
    #     r_string = r[i].split(',')
    #     reaction = map(float, r_string)
    #     key = int(reaction[0]) - 1
    #     if all(v == 0.0 for v in reaction) is False:
    #         react_dict[key] = {'rxx': reaction[3], 'ryy': reaction[4], 'rzz': reaction[5],
    #                            'rx': reaction[0], 'ry': reaction[1], 'rz': reaction[2]}

    react_dict = {'rmx': {}, 'rmy': {}, 'rmz': {}, 'rfx': {}, 'rfy': {}, 'rfz': {}, 'rfm': {}}
    for i in range(len(r)):
        r_string = r[i].split(',')
        reaction = map(float, r_string[1:])
        key = int(reaction[0]) - 1
        if all(v == 0.0 for v in reaction) is False:
            react_dict['rmx'][key] = float(reaction[4])
            react_dict['rmy'][key] = float(reaction[5])
            react_dict['rmz'][key] = float(reaction[6])
            react_dict['rfx'][key] = float(reaction[1])
            react_dict['rfy'][key] = float(reaction[2])
            react_dict['rfz'][key] = float(reaction[3])
            react_dict['rfm'][key] = length_vector([reaction[1], reaction[2], reaction[3]])
    return react_dict
Beispiel #27
0
def face_skewnesses(mesh):
    """Skewnesses of the mesh faces as dict face: face skewness.

	https://en.wikipedia.org/wiki/Types_of_mesh

	Parameters
	----------
	mesh : Mesh
		A mesh.

	Returns
	-------
	face_aspect_ratio_dict: dict
		Dictionary of aspect ratios per face {face: face aspect ratio}.

	Raises
	------
	-

	"""

    face_skewness_dict = {}
    for fkey in mesh.faces():
        equi_angle = 180 * (1 - 2 / float(len(mesh.face_vertices(fkey))))
        angles = []
        face_vertices = mesh.face_vertices(fkey)
        for i in range(len(face_vertices)):
            u = mesh.vertex_coordinates(face_vertices[i - 2])
            v = mesh.vertex_coordinates(face_vertices[i - 1])
            w = mesh.vertex_coordinates(face_vertices[i])
            uv = subtract_vectors(v, u)
            vw = subtract_vectors(w, v)
            dot = dot_vectors(uv, vw) / (length_vector(uv) * length_vector(vw))
            cross = dot_vectors(mesh.face_normal(fkey), cross_vectors(uv, vw))
            sign = 1
            if sign < 0:
                sign = -1
            angle = sign * degrees(acos(dot))
            angles.append(angle)
        max_angle = maximum(angles)
        min_angle = minimum(angles)

        face_skewness_dict[fkey] = max(
            (max_angle - equi_angle) / (180 - equi_angle),
            (equi_angle - min_angle) / equi_angle)

    return face_skewness_dict
Beispiel #28
0
 def edge_avg_length(self):
     sum_length = 0
     edge_count = 0
     for u, v in self.edges_iter():
         edge_vector = self.edge_vector(u, v, unitized=False)
         sum_length += length_vector(edge_vector)
         edge_count += 1
     return sum_length / edge_count
Beispiel #29
0
 def face_normal(self, fkey, unitized=True):
     points = self.face_coordinates(fkey)
     normal = polygon_normal_oriented(points, unitized)
     if length_vector(normal) == 0:
         uv = subtract_vectors(points[1], points[0])
         vw = subtract_vectors(points[2], points[1])
         normal = normalize_vector(cross_vectors(uv, vw))
     return normal
Beispiel #30
0
def polyedge_curvatures(mesh, polyedges):
    """Curvatures of the mesh vertices along polyedges as dict (vertices): (curvatures).


	Parameters
	----------
	mesh: Mesh
		A mesh
	polyedges: list
		List of polyedges as sequences of vertices.

	Returns
	-------
	polyedge_curvature_dict: dict
		Dictionary of curvatures per vertex per polyedge {(vertices): (curvature)}.

	Raises
	------
	-

	"""

    polyedge_curvature_dict = {}
    for polyedge in polyedges:
        curvatures = []
        for i in range(len(polyedge)):
            if i == 0 or i == len(polyedge) - 1:
                curvatures.append(0)
            else:
                a, b, c = polyedge[i - 1], polyedge[i], polyedge[i + 1]
                ab = subtract_vectors(mesh.vertex_coordinates(b),
                                      mesh.vertex_coordinates(a))
                bc = subtract_vectors(mesh.vertex_coordinates(c),
                                      mesh.vertex_coordinates(b))
                ac = subtract_vectors(mesh.vertex_coordinates(c),
                                      mesh.vertex_coordinates(a))
                if cross_vectors(ab, bc) == 0:
                    curvatures.append(0)
                else:
                    radius = length_vector(ac) / (2 * length_vector(
                        cross_vectors(ab, bc))) * (length_vector(ab) *
                                                   length_vector(bc))
                    curvatures.append(1 / radius)
        polyedge_curvature_dict[tuple(polyedge)] = curvatures

    return polyedge_curvature_dict