示例#1
0
 def normal(self, surface_point: tuple) -> tuple:
     on_surf, surf_indexes = on_aabb_surface(self._size, surface_point,  atol=2*EPS_ZERO)
     if not on_surf:
         raise GeometryError(
             "Point is not on surface.",
             {"point": surface_point, "geometry": self}
         )
     if len(surf_indexes) != 1:
         raise GeometryError(
             "Point is on multiple surfaces.",
             {"point": surface_point, "geometry": self}
         )
     idx = surf_indexes[0]
     # normal vector in the local frame
     return NORMALS[idx]
示例#2
0
 def normal(self, surface_point: tuple) -> tuple:
     """ Returns the unit surface normal at the surface_point.
     """
     mesh = self.trimesh
     (closest_points, distances,
      triangle_id) = mesh.nearest.on_surface(np.array([surface_point]))
     if closest_points.shape != (1, 3):
         raise GeometryError(
             'Mesh must have a single closest point to calculate normal.')
     if not np.any(np.absolute(distances) < EPS_ZERO):
         raise GeometryError(
             'Point is not on surface.', {
                 "point": surface_point,
                 "geometry": self,
                 "distances": distances,
                 "threshold": EPS_ZERO
             })
     normal = tuple(mesh.face_normals[triangle_id[0]])
     return normal
示例#3
0
 def is_entering(self, surface_point, direction) -> bool:
     """ Returns True if the ray at surface point with direction is heading 
     into the shape. This is tested by checking for a negative dot product between
     the vectors.
     """
     if not self.is_on_surface(surface_point):
         raise GeometryError("Not a surface point.")
     normal = self.normal(surface_point)
     if np.dot(normal, direction) < 0.0:
         return True
     return False
示例#4
0
 def normal(self, surface_point):
     """ Normal faces outwards by convention.
     """
     z = surface_point[2]
     if np.isclose(z, -0.5 * self.length):
         return (0.0, 0.0, -1.0)
     elif np.isclose(z, 0.5 * self.length):
         return (0.0, 0.0, 1.0)
     elif np.isclose(self.radius, np.sqrt(np.sum(np.array(surface_point[:2]) ** 2))):
         v = np.array(surface_point) - np.array([0.0, 0.0, surface_point[2]])
         n = tuple(norm(v).tolist())
         return n
     else:
         raise GeometryError("Not a surface point.")