def clip(self, center, size): """ clip self in square of given size at given center. """ # TODO move in elementary path points = [ center + Point([-size, -size]), center + Point([size, -size]), center + Point([size, size]), center + Point([-size, size]), ] segments = [Segment([a, b]) for a, b in all_two_elements(points)] intersections = [] for segment in segments: intersection = segment.intersection_with_segment(self) if intersection: intersections.append(intersection) box = BoundingBox.empty_box(2) box.add_point(points[0]) box.add_point(points[2]) for chunk in self.split_at(intersections): middle = (chunk.endpoints[0] + chunk.endpoints[1]) / 2 if box.almost_contains_point(middle): return chunk
def polygon_segments(height, polygon): """ iterates on all PolygonSegment inside a given polygon at a given height """ for start, end in all_two_elements(polygon.points): yield PolygonSegment([start, end], height, polygon)
def join_raw_segments(self, raw_segments): """ reconnect all parallel segments. """ for neighbouring_tuples in all_two_elements(raw_segments): first_segment, second_segment = [p[0] for p in neighbouring_tuples] end = first_segment.endpoints[1] start = second_segment.endpoints[0] if end.is_almost(start): first_segment = Segment([first_segment.endpoints[0], start]) else: # original point connecting the original segments center_point = neighbouring_tuples[0][1].endpoints[1] # add arc try: binding = Arc(self.radius, [end, start], center_point) binding.adjust_center() binding.correct_endpoints_order() except: print("failed joining segments") tycat(self.polygon, center_point, first_segment, second_segment) raise self.edge.append(first_segment) self.edge.append(binding) if __debug__: if is_module_debugged(__name__): print("joined segments") tycat(self.polygon, self.edge)
def __init__(self, inside_content, distance): """ inflates path by given distance """ self.distance = distance self.inside_content = inside_content # for debug only if isinstance(inside_content, Pocket): inside = inside_content.paths else: inside = (inside_content, inside_content.reverse()) try: self.paths = [] # just follow path, moving away raw_paths = [DisplacedPath.displace(p, distance) for p in inside] # and then reconnecting everything. for path1, path2 in all_two_elements(raw_paths): self.paths.extend(path1.reconnect(path2, distance)) except: print("failed compute envelope for", self.inside_content) tycat(self.inside_content, [p.path for p in raw_paths]) raise if __debug__: if is_module_debugged(__name__): print("inflating") tycat(self)
def area(self): """ return polygon area. can be positive or negative, depending on orientation. """ return sum( [p1.cross_product(p2) for p1, p2 in all_two_elements(self.points)]) / 2
def border_2d(stl_model, margin): """ return 2d enclosing (starting at origin) for given model and margin. """ # build four points xmin, ymin = 0, 0 xmax, ymax = stl_model.dimensions(margin) points = [] points.append(Point([xmin, ymin])) points.append(Point([xmin, ymax])) points.append(Point([xmax, ymax])) points.append(Point([xmax, ymin])) return [Segment([p, q]) for p, q in all_two_elements(points)]
def segments(self): """ iterate through all segments. """ for points in all_two_elements(self.points): yield Segment(points)
including = Polygon.square(-1, 4, 3) including_pocket = Pocket(list(including.segments())) not_including = [ Point([-2.0, 3.0]), Point([-2.0, 2.0]), Point([9.0, 2.0]), Point([9.0, 10.0]), Point([-2.0, 10.0]), Point([-2.0, 9.0]), Point([8.0, 9.0]), Point([8.0, 3.0]), ] not_including_pocket = Pocket( [Segment([a, b]) for a, b in all_two_elements(not_including)]) vertically_aligned = [ Point([-1, 3.5]), Point([2, 3.5]), Point([4, 5.5]), Point([2, 7.5]), Point([-1, 7.5]), Point([-4, 5.5]), ] va_pocket = Pocket( [Segment([a, b]) for a, b in all_two_elements(vertically_aligned)]) if tested_pocket.is_included_in(including_pocket): print("red is included in green (ok)")