From f3d066d2bcc294701b80b245ac4f92d5bd05d32d Mon Sep 17 00:00:00 2001 From: Simon Cross Date: Sat, 10 Sep 2016 22:06:55 +0200 Subject: [PATCH] Use bounding foxes. --- tabakrolletjie/rays.py | 32 ++++++++++++++++++++------------ 1 file changed, 20 insertions(+), 12 deletions(-) diff --git a/tabakrolletjie/rays.py b/tabakrolletjie/rays.py index 8b53278..7d880d0 100644 --- a/tabakrolletjie/rays.py +++ b/tabakrolletjie/rays.py @@ -8,30 +8,30 @@ import pymunk import pymunk.autogeometry import pymunk.pygame_util -from .constants import SCREEN_SIZE from .utils import debug_timer -def screen_rays(): +def screen_rays(pos, bounding_radius): """ An iterable that returns ordered rays from pos to the edge of the screen, starting with the edge point (0, 0) and continuing clockwise in pymunk coordinates. """ - w, h = SCREEN_SIZE - left, right, bottom, top = 0, w, 0, h + r = int(bounding_radius) + left, right = int(pos.x) - r, int(pos.x) + r + bottom, top = int(pos.y) + r, int(pos.y) - r step = 1 - for y in range(0, h, step): + for y in range(top, bottom + 1, step): yield pymunk.Vec2d(left, y) - for x in range(0, w, step): + for x in range(left, right + 1, step): yield pymunk.Vec2d(x, top) - for y in range(top, -1, -step): + for y in range(bottom, top - 1, -step): yield pymunk.Vec2d(right, y) - for x in range(right, -1, -step): + for x in range(right, left - 1, -step): yield pymunk.Vec2d(x, bottom) @debug_timer("rays.calculate_ray_polys") -def calculate_ray_polys(space, position, light_filter): +def calculate_ray_polys(space, position, bounding_radius, light_filter): """ Calculate a set of convex RayPolys that cover all the areas that light can reach from the given position, taking into account the obstacles present in the space. @@ -40,7 +40,7 @@ def calculate_ray_polys(space, position, light_filter): vertices = [position] start, end = None, None ray_polys = [] - for ray in screen_rays(): + for ray in screen_rays(position, bounding_radius): info = space.segment_query_first(position, ray, 1, light_filter) point = ray if info is None else info.point vertices.append(point) @@ -79,7 +79,7 @@ def to_pymunk_radians(deg): class RayPolyManager(object): def __init__( self, body, position, ray_filter, radius_limits, direction, - spread): + spread, bounding_radius): self._body = body # light's body self._position = pymunk.Vec2d(position) # light's position self._ray_filter = ray_filter # light filter @@ -88,11 +88,13 @@ class RayPolyManager(object): self._start = None # normal vector in direction of start angle limit self._end = None # normal vector in direction of end angle limit self._set_angle_limits(direction, spread) + self._bounding_radius = None # absolute maximum radius if direction: self.direction = direction # Update direction self._max_radius = None # maximum radius in pixels self._min_radius = None # minimum radius in pixels self._set_radius_limits(radius_limits) + self._set_bounding_radius(bounding_radius) self._old_poly_cache = None # last polys added to the space self._poly_cache = None # list of pymunk.Polys for rays self._space = None # space the rays form part of @@ -100,7 +102,8 @@ class RayPolyManager(object): def set_space(self, space): self._space = space self._rays = calculate_ray_polys( - self._space, self._position, self._ray_filter) + self._space, self._position, self._bounding_radius, + self._ray_filter) self._poly_cache = None def update_shapes(self): @@ -157,6 +160,11 @@ class RayPolyManager(object): else: self._max_radius = radius_limits[1] + def _set_bounding_radius(self, bounding_radius): + if bounding_radius is None: + bounding_radius = self._max_radius + self._bounding_radius = bounding_radius + def rotatable(self): return self._direction is not None -- 2.34.1