From 782fd9138f9032ae7175d56ba0ccaffc780e515f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Laura=20Kl=C3=BCnder?= Date: Mon, 19 Dec 2016 20:10:25 +0100 Subject: [PATCH] add points aroung arealocations and excludables --- src/c3nav/routing/level.py | 23 +++++++++++++++---- src/c3nav/routing/room.py | 47 ++++++++++++++++++++------------------ 2 files changed, 44 insertions(+), 26 deletions(-) diff --git a/src/c3nav/routing/level.py b/src/c3nav/routing/level.py index d34a70f3..955c663c 100644 --- a/src/c3nav/routing/level.py +++ b/src/c3nav/routing/level.py @@ -126,10 +126,10 @@ class GraphLevel(): self._built_arealocations = {} self._built_excludables = {} - for arealocation in self.level.arealocations.all(): - self._built_arealocations[arealocation.name] = arealocation.geometry - if arealocation.routing_inclusion != 'default' or arealocation.package not in public_packages: - self._built_excludables[arealocation.name] = arealocation.geometry + for excludable in self.level.arealocations.all(): + self._built_arealocations[excludable.name] = excludable.geometry + if excludable.routing_inclusion != 'default' or excludable.package not in public_packages: + self._built_excludables[excludable.name] = excludable.geometry public_area, private_area = get_public_private_area(self.level) @@ -139,6 +139,21 @@ class GraphLevel(): self._built_arealocations[':private'] = private_area self._built_excludables[':private'] = private_area + # add points inside arealocations to be able to route to its borders + for excludable in self._built_arealocations.values(): + smaller = excludable.buffer(-0.05, join_style=JOIN_STYLE.mitre) + for room in self.rooms: + room.add_points_on_rings(assert_multipolygon(smaller)) + + # add points outside excludables so if excluded you can walk around them + for excludable in self._built_excludables.values(): + for polygon in assert_multipolygon(excludable.buffer(0.28, join_style=JOIN_STYLE.mitre)): + for room in self.rooms: + room._add_ring(polygon.exterior, want_left=True) + + for interior in polygon.interiors: + room._add_ring(interior, want_left=False) + def create_doors(self): doors = self.level.geometries.doors doors = assert_multipolygon(doors) diff --git a/src/c3nav/routing/room.py b/src/c3nav/routing/room.py index 29e967a8..802d9341 100644 --- a/src/c3nav/routing/room.py +++ b/src/c3nav/routing/room.py @@ -129,28 +129,7 @@ class GraphRoom(): points += self._add_ring(interior, want_left=True) # points around steps - for polygon in self._built_isolated_areas: - for ring in (polygon.exterior, )+tuple(polygon.interiors): - for linestring in assert_multilinestring(ring.intersection(self.clear_geometry)): - coords = tuple(linestring.coords) - if len(coords) == 2: - path = Path(coords) - length = abs(np.linalg.norm(path.vertices[0] - path.vertices[1])) - for coord in tuple(path.interpolated(int(length / 1.0 + 1)).vertices): - self.add_point(coord) - continue - - start = 0 - for segment in zip(coords[:-1], coords[1:]): - path = Path(segment) - length = abs(np.linalg.norm(path.vertices[0] - path.vertices[1])) - if length < 1.0: - coords = (path.vertices[1 if start == 0 else 0], ) - else: - coords = tuple(path.interpolated(int(length / 1.0 + 0.5)).vertices)[start:] - for coord in coords: - self.add_point(coord) - start = 1 + self.add_points_on_rings(self._built_isolated_areas) def _add_ring(self, geom, want_left): """ @@ -186,6 +165,30 @@ class GraphRoom(): return points + def add_points_on_rings(self, areas): + for polygon in areas: + for ring in (polygon.exterior,) + tuple(polygon.interiors): + for linestring in assert_multilinestring(ring.intersection(self.clear_geometry)): + coords = tuple(linestring.coords) + if len(coords) == 2: + path = Path(coords) + length = abs(np.linalg.norm(path.vertices[0] - path.vertices[1])) + for coord in tuple(path.interpolated(int(length / 1.0 + 1)).vertices): + self.add_point(coord) + continue + + start = 0 + for segment in zip(coords[:-1], coords[1:]): + path = Path(segment) + length = abs(np.linalg.norm(path.vertices[0] - path.vertices[1])) + if length < 1.0: + coords = (path.vertices[1 if start == 0 else 0],) + else: + coords = tuple(path.interpolated(int(length / 1.0 + 0.5)).vertices)[start:] + for coord in coords: + self.add_point(coord) + start = 1 + def add_point(self, coord): if not self.mpl_clear.contains_point(coord): return []