Issues (838)

tdl/map.py (37 issues)

1
"""
2
    Rogue-like map utilitys such as line-of-sight, field-of-view, and path-finding.
0 ignored issues
show
This line is too long as per the coding-style (83/80).

This check looks for lines that are too long. You can specify the maximum line length.

Loading history...
3
4
    .. deprecated:: 3.2
5
        The features provided here are better realized in the
6
        :any:`tcod.map` and :any:`tcod.path` modules.
7
"""
8
9
from __future__ import absolute_import
10
11
import itertools as _itertools
12
import math as _math
13
14
import numpy as np
0 ignored issues
show
The import numpy could not be resolved.

This can be caused by one of the following:

1. Missing Dependencies

This error could indicate a configuration issue of Pylint. Make sure that your libraries are available by adding the necessary commands.

# .scrutinizer.yml
before_commands:
    - sudo pip install abc # Python2
    - sudo pip3 install abc # Python3
Tip: We are currently not using virtualenv to run pylint, when installing your modules make sure to use the command for the correct version.

2. Missing __init__.py files

This error could also result from missing __init__.py files in your module folders. Make sure that you place one file in each sub-folder.

Loading history...
15
16
from tcod import ffi as _ffi
17
from tcod import lib as _lib
18
from tcod import ffi, lib
0 ignored issues
show
The import ffi was already done on line 16. You should be able to
remove this line.
Loading history...
The import lib was already done on line 17. You should be able to
remove this line.
Loading history...
Unused ffi imported from tcod
Loading history...
19
20
import tcod.map
21
import tcod.path
22
import tdl as _tdl
23
from . import style as _style
24
25
_FOVTYPES = {'BASIC' : 0, 'DIAMOND': 1, 'SHADOW': 2, 'RESTRICTIVE': 12,
26
             'PERMISSIVE': 11}
27
28
def _get_fov_type(fov):
29
    "Return a FOV from a string"
30
    oldFOV = fov
0 ignored issues
show
Coding Style Naming introduced by
The name oldFOV does not conform to the variable naming conventions ([a-z_][a-z0-9_]{2,30}$).

This check looks for invalid names for a range of different identifiers.

You can set regular expressions to which the identifiers must conform if the defaults do not match your requirements.

If your project includes a Pylint configuration file, the settings contained in that file take precedence.

To find out more about Pylint, please refer to their site.

Loading history...
31
    fov = str(fov).upper()
32
    if fov in _FOVTYPES:
33
        return _FOVTYPES[fov]
34
    if fov[:10] == 'PERMISSIVE' and fov[10].isdigit() and fov[10] != '9':
35
        return 4 + int(fov[10])
36
    raise _tdl.TDLError('No such fov option as %s' % oldFOV)
37
38
class Map(tcod.map.Map):
39
    """Field-of-view and path-finding on stored data.
40
41
    .. versionchanged:: 4.1
42
        `transparent`, `walkable`, and `fov` are now numpy boolean arrays.
43
44
    .. versionchanged:: 4.3
45
        Added `order` parameter.
46
47
    .. deprecated:: 3.2
48
        :any:`tcod.map.Map` should be used instead.
49
50
    Set map conditions with the walkable and transparency attributes, this
51
    object can be iterated and checked for containment similar to consoles.
52
53
    For example, you can set all tiles and transparent and walkable with the
54
    following code:
55
56
    Example:
57
        >>> import tdl.map
58
        >>> map_ = tdl.map.Map(80, 60)
59
        >>> map_.transparent[:] = True
60
        >>> map_.walkable[:] = True
61
62
    Attributes:
63
        transparent: Map transparency
64
65
            Access this attribute with ``map.transparent[x,y]``
66
67
            Set to True to allow field-of-view rays, False will
68
            block field-of-view.
69
70
            Transparent tiles only affect field-of-view.
71
        walkable: Map accessibility
72
73
            Access this attribute with ``map.walkable[x,y]``
74
75
            Set to True to allow path-finding through that tile,
76
            False will block passage to that tile.
77
78
            Walkable tiles only affect path-finding.
79
80
        fov: Map tiles touched by a field-of-view computation.
81
82
            Access this attribute with ``map.fov[x,y]``
83
84
            Is True if a the tile is if view, otherwise False.
85
86
            You can set to this attribute if you want, but you'll typically
87
            be using it to read the field-of-view of a :any:`compute_fov` call.
88
    """
89
90
    def __init__(self, width, height, order='F'):
91
        super(Map, self).__init__(width, height, order)
92
93
    def compute_fov(self, x, y, fov='PERMISSIVE', radius=None,
0 ignored issues
show
Arguments number differs from overridden 'compute_fov' method
Loading history...
94
                    light_walls=True, sphere=True, cumulative=False):
0 ignored issues
show
The argument sphere seems to be unused.
Loading history...
95
        """Compute the field-of-view of this Map and return an iterator of the
96
        points touched.
97
98
        Args:
99
            x (int): Point of view, x-coordinate.
100
            y (int): Point of view, y-coordinate.
101
            fov (Text): The type of field-of-view to be used.
102
103
                Available types are:
104
                'BASIC', 'DIAMOND', 'SHADOW', 'RESTRICTIVE', 'PERMISSIVE',
105
                'PERMISSIVE0', 'PERMISSIVE1', ..., 'PERMISSIVE8'
106
            radius (Optional[int]): Maximum view distance from the point of
107
                view.
108
109
                A value of 0 will give an infinite distance.
110
            light_walls (bool): Light up walls, or only the floor.
111
            sphere (bool): If True the lit area will be round instead of
112
                square.
113
            cumulative (bool): If True the lit cells will accumulate instead
114
                of being cleared before the computation.
115
116
        Returns:
117
            Iterator[Tuple[int, int]]: An iterator of (x, y) points of tiles
118
                touched by the field-of-view.
119
        """
120
        # refresh cdata
121
        if radius is None: # infinite radius
122
            radius = 0
123
        if cumulative:
124
            fov_copy = self.fov.copy()
125
        lib.TCOD_map_compute_fov(
126
            self.map_c, x, y, radius, light_walls, _get_fov_type(fov))
127
        if cumulative:
128
            self.fov[:] |= fov_copy
129
        return zip(*np.where(self.fov))
130
131
132
    def compute_path(self, start_x, start_y, dest_x, dest_y,
133
                     diagonal_cost=_math.sqrt(2)):
134
        """Get the shortest path between two points.
135
136
        Args:
137
            start_x (int): Starting x-position.
138
            start_y (int): Starting y-position.
139
            dest_x (int): Destination x-position.
140
            dest_y (int): Destination y-position.
141
            diagonal_cost (float): Multiplier for diagonal movement.
142
143
                Can be set to zero to disable diagonal movement entirely.
144
145
        Returns:
146
            List[Tuple[int, int]]: The shortest list of points to the
147
                destination position from the starting position.
148
149
            The start point is not included in this list.
150
        """
151
        return tcod.path.AStar(self, diagonal_cost).get_path(start_x, start_y,
152
                                                             dest_x, dest_y)
153
154
    def __iter__(self):
155
        return _itertools.product(range(self.width), range(self.height))
156
157
    def __contains__(self, position):
158
        x, y = position
0 ignored issues
show
Coding Style Naming introduced by
The name x does not conform to the variable naming conventions ([a-z_][a-z0-9_]{2,30}$).

This check looks for invalid names for a range of different identifiers.

You can set regular expressions to which the identifiers must conform if the defaults do not match your requirements.

If your project includes a Pylint configuration file, the settings contained in that file take precedence.

To find out more about Pylint, please refer to their site.

Loading history...
Coding Style Naming introduced by
The name y does not conform to the variable naming conventions ([a-z_][a-z0-9_]{2,30}$).

This check looks for invalid names for a range of different identifiers.

You can set regular expressions to which the identifiers must conform if the defaults do not match your requirements.

If your project includes a Pylint configuration file, the settings contained in that file take precedence.

To find out more about Pylint, please refer to their site.

Loading history...
159
        return (0 <= x < self.width) and (0 <= y < self.height)
160
161
162
163
class AStar(tcod.path.AStar):
164
    """An A* pathfinder using a callback.
165
166
    .. deprecated:: 3.2
167
        See :any:`tcod.path`.
168
169
    Before crating this instance you should make one of two types of
170
    callbacks:
171
172
    - A function that returns the cost to move to (x, y)
173
    - A function that returns the cost to move between
174
      (destX, destY, sourceX, sourceY)
175
176
    If path is blocked the function should return zero or None.
177
    When using the second type of callback be sure to set advanced=True
178
179
    Args:
180
        width (int): Width of the pathfinding area (in tiles.)
181
        height (int): Height of the pathfinding area (in tiles.)
182
        callback (Union[Callable[[int, int], float],
183
                        Callable[[int, int, int, int], float]]): A callback
184
            returning the cost of a tile or edge.
185
186
            A callback taking parameters depending on the setting
187
            of 'advanced' and returning the cost of
188
            movement for an open tile or zero for a
189
            blocked tile.
190
        diagnalCost (float): Multiplier for diagonal movement.
191
192
            Can be set to zero to disable diagonal movement entirely.
193
        advanced (bool): Give 2 additional parameters to the callback.
194
195
            A simple callback with 2 positional parameters may not
196
            provide enough information.  Setting this to True will
197
            call the callback with 2 additional parameters giving
198
            you both the destination and the source of movement.
199
200
            When True the callback will need to accept
201
            (destX, destY, sourceX, sourceY) as parameters.
202
            Instead of just (destX, destY).
203
    """
204
205
    class __DeprecatedEdgeCost(tcod.path.EdgeCostCallback):
0 ignored issues
show
Coding Style Naming introduced by
The name __DeprecatedEdgeCost does not conform to the class naming conventions ([A-Z_][a-zA-Z0-9]+$).

This check looks for invalid names for a range of different identifiers.

You can set regular expressions to which the identifiers must conform if the defaults do not match your requirements.

If your project includes a Pylint configuration file, the settings contained in that file take precedence.

To find out more about Pylint, please refer to their site.

Loading history...
This class should have a docstring.

The coding style of this project requires that you add a docstring to this code element. Below, you find an example for methods:

class SomeClass:
    def some_method(self):
        """Do x and return foo."""

If you would like to know more about docstrings, we recommend to read PEP-257: Docstring Conventions.

Loading history...
206
        _CALLBACK_P = lib._pycall_path_swap_src_dest
207
208
    class __DeprecatedNodeCost(tcod.path.EdgeCostCallback):
0 ignored issues
show
Coding Style Naming introduced by
The name __DeprecatedNodeCost does not conform to the class naming conventions ([A-Z_][a-zA-Z0-9]+$).

This check looks for invalid names for a range of different identifiers.

You can set regular expressions to which the identifiers must conform if the defaults do not match your requirements.

If your project includes a Pylint configuration file, the settings contained in that file take precedence.

To find out more about Pylint, please refer to their site.

Loading history...
This class should have a docstring.

The coding style of this project requires that you add a docstring to this code element. Below, you find an example for methods:

class SomeClass:
    def some_method(self):
        """Do x and return foo."""

If you would like to know more about docstrings, we recommend to read PEP-257: Docstring Conventions.

Loading history...
209
        _CALLBACK_P = lib._pycall_path_dest_only
210
211
    def __init__(self, width, height, callback,
212
                 diagnalCost=_math.sqrt(2), advanced=False):
213
        if advanced:
214
            cost = self.__DeprecatedEdgeCost(callback, width, height)
215
        else:
216
            cost = self.__DeprecatedNodeCost(callback, width, height)
217
        super(AStar, self).__init__(cost, diagnalCost or 0.0)
218
219
    def get_path(self, origX, origY, destX, destY):
220
        """
221
        Get the shortest path from origXY to destXY.
222
223
        Returns:
224
            List[Tuple[int, int]]: Returns a list walking the path from orig
225
                to dest.
226
227
                This excludes the starting point and includes the destination.
228
229
                If no path is found then an empty list is returned.
230
        """
231
        return super(AStar, self).get_path(origX, origY, destX, destY)
232
233
def quick_fov(x, y, callback, fov='PERMISSIVE', radius=7.5, lightWalls=True,
0 ignored issues
show
Coding Style Naming introduced by
The name x does not conform to the argument naming conventions ([a-z_][a-z0-9_]{2,30}$).

This check looks for invalid names for a range of different identifiers.

You can set regular expressions to which the identifiers must conform if the defaults do not match your requirements.

If your project includes a Pylint configuration file, the settings contained in that file take precedence.

To find out more about Pylint, please refer to their site.

Loading history...
Coding Style Naming introduced by
The name y does not conform to the argument naming conventions ([a-z_][a-z0-9_]{2,30}$).

This check looks for invalid names for a range of different identifiers.

You can set regular expressions to which the identifiers must conform if the defaults do not match your requirements.

If your project includes a Pylint configuration file, the settings contained in that file take precedence.

To find out more about Pylint, please refer to their site.

Loading history...
Coding Style Naming introduced by
The name lightWalls does not conform to the argument naming conventions ([a-z_][a-z0-9_]{2,30}$).

This check looks for invalid names for a range of different identifiers.

You can set regular expressions to which the identifiers must conform if the defaults do not match your requirements.

If your project includes a Pylint configuration file, the settings contained in that file take precedence.

To find out more about Pylint, please refer to their site.

Loading history...
234
              sphere=True):
235
    """All field-of-view functionality in one call.
236
237
    Before using this call be sure to make a function, lambda, or method that takes 2
0 ignored issues
show
This line is too long as per the coding-style (85/80).

This check looks for lines that are too long. You can specify the maximum line length.

Loading history...
238
    positional parameters and returns True if light can pass through the tile or False
0 ignored issues
show
This line is too long as per the coding-style (86/80).

This check looks for lines that are too long. You can specify the maximum line length.

Loading history...
239
    for light-blocking tiles and for indexes that are out of bounds of the
240
    dungeon.
241
242
    This function is 'quick' as in no hassle but can quickly become a very slow
243
    function call if a large radius is used or the callback provided itself
244
    isn't optimized.
245
246
    Always check if the index is in bounds both in the callback and in the
247
    returned values.  These values can go into the negatives as well.
248
249
    Args:
250
        x (int): x center of the field-of-view
251
        y (int): y center of the field-of-view
252
        callback (Callable[[int, int], bool]):
253
254
            This should be a function that takes two positional arguments x,y
255
            and returns True if the tile at that position is transparent
256
            or False if the tile blocks light or is out of bounds.
257
        fov (Text): The type of field-of-view to be used.
258
259
            Available types are:
260
            'BASIC', 'DIAMOND', 'SHADOW', 'RESTRICTIVE', 'PERMISSIVE',
261
            'PERMISSIVE0', 'PERMISSIVE1', ..., 'PERMISSIVE8'
262
        radius (float) Radius of the field-of-view.
263
264
            When sphere is True a floating point can be used to fine-tune
265
            the range.  Otherwise the radius is just rounded up.
266
267
            Be careful as a large radius has an exponential affect on
268
            how long this function takes.
269
        lightWalls (bool): Include or exclude wall tiles in the field-of-view.
270
        sphere (bool): True for a spherical field-of-view.
271
            False for a square one.
272
273
    Returns:
274
        Set[Tuple[int, int]]: A set of (x, y) points that are within the
275
            field-of-view.
276
    """
277
    trueRadius = radius
0 ignored issues
show
Coding Style Naming introduced by
The name trueRadius does not conform to the variable naming conventions ([a-z_][a-z0-9_]{2,30}$).

This check looks for invalid names for a range of different identifiers.

You can set regular expressions to which the identifiers must conform if the defaults do not match your requirements.

If your project includes a Pylint configuration file, the settings contained in that file take precedence.

To find out more about Pylint, please refer to their site.

Loading history...
278
    radius = int(_math.ceil(radius))
279
    mapSize = radius * 2 + 1
0 ignored issues
show
Coding Style Naming introduced by
The name mapSize does not conform to the variable naming conventions ([a-z_][a-z0-9_]{2,30}$).

This check looks for invalid names for a range of different identifiers.

You can set regular expressions to which the identifiers must conform if the defaults do not match your requirements.

If your project includes a Pylint configuration file, the settings contained in that file take precedence.

To find out more about Pylint, please refer to their site.

Loading history...
280
    fov = _get_fov_type(fov)
281
282
    setProp = _lib.TCOD_map_set_properties # make local
0 ignored issues
show
Coding Style Naming introduced by
The name setProp does not conform to the variable naming conventions ([a-z_][a-z0-9_]{2,30}$).

This check looks for invalid names for a range of different identifiers.

You can set regular expressions to which the identifiers must conform if the defaults do not match your requirements.

If your project includes a Pylint configuration file, the settings contained in that file take precedence.

To find out more about Pylint, please refer to their site.

Loading history...
283
    inFOV = _lib.TCOD_map_is_in_fov
0 ignored issues
show
Coding Style Naming introduced by
The name inFOV does not conform to the variable naming conventions ([a-z_][a-z0-9_]{2,30}$).

This check looks for invalid names for a range of different identifiers.

You can set regular expressions to which the identifiers must conform if the defaults do not match your requirements.

If your project includes a Pylint configuration file, the settings contained in that file take precedence.

To find out more about Pylint, please refer to their site.

Loading history...
284
285
    tcodMap = _lib.TCOD_map_new(mapSize, mapSize)
0 ignored issues
show
Coding Style Naming introduced by
The name tcodMap does not conform to the variable naming conventions ([a-z_][a-z0-9_]{2,30}$).

This check looks for invalid names for a range of different identifiers.

You can set regular expressions to which the identifiers must conform if the defaults do not match your requirements.

If your project includes a Pylint configuration file, the settings contained in that file take precedence.

To find out more about Pylint, please refer to their site.

Loading history...
286
    try:
287
        # pass no.1, write callback data to the tcodMap
288
        for x_, y_ in _itertools.product(range(mapSize), range(mapSize)):
0 ignored issues
show
Coding Style Naming introduced by
The name x_ does not conform to the variable naming conventions ([a-z_][a-z0-9_]{2,30}$).

This check looks for invalid names for a range of different identifiers.

You can set regular expressions to which the identifiers must conform if the defaults do not match your requirements.

If your project includes a Pylint configuration file, the settings contained in that file take precedence.

To find out more about Pylint, please refer to their site.

Loading history...
Coding Style Naming introduced by
The name y_ does not conform to the variable naming conventions ([a-z_][a-z0-9_]{2,30}$).

This check looks for invalid names for a range of different identifiers.

You can set regular expressions to which the identifiers must conform if the defaults do not match your requirements.

If your project includes a Pylint configuration file, the settings contained in that file take precedence.

To find out more about Pylint, please refer to their site.

Loading history...
289
            pos = (x_ + x - radius,
290
                   y_ + y - radius)
291
            transparent = bool(callback(*pos))
292
            setProp(tcodMap, x_, y_, transparent, False)
293
294
        # pass no.2, compute fov and build a list of points
295
        _lib.TCOD_map_compute_fov(tcodMap, radius, radius, radius, lightWalls, fov)
0 ignored issues
show
This line is too long as per the coding-style (83/80).

This check looks for lines that are too long. You can specify the maximum line length.

Loading history...
296
        touched = set() # points touched by field of view
297
        for x_, y_ in _itertools.product(range(mapSize), range(mapSize)):
0 ignored issues
show
Coding Style Naming introduced by
The name x_ does not conform to the variable naming conventions ([a-z_][a-z0-9_]{2,30}$).

This check looks for invalid names for a range of different identifiers.

You can set regular expressions to which the identifiers must conform if the defaults do not match your requirements.

If your project includes a Pylint configuration file, the settings contained in that file take precedence.

To find out more about Pylint, please refer to their site.

Loading history...
Coding Style Naming introduced by
The name y_ does not conform to the variable naming conventions ([a-z_][a-z0-9_]{2,30}$).

This check looks for invalid names for a range of different identifiers.

You can set regular expressions to which the identifiers must conform if the defaults do not match your requirements.

If your project includes a Pylint configuration file, the settings contained in that file take precedence.

To find out more about Pylint, please refer to their site.

Loading history...
298
            if sphere and _math.hypot(x_ - radius, y_ - radius) > trueRadius:
299
                continue
300
            if inFOV(tcodMap, x_, y_):
301
                touched.add((x_ + x - radius, y_ + y - radius))
302
    finally:
303
        _lib.TCOD_map_delete(tcodMap)
304
    return touched
305
306
def bresenham(x1, y1, x2, y2):
0 ignored issues
show
Coding Style Naming introduced by
The name x1 does not conform to the argument naming conventions ([a-z_][a-z0-9_]{2,30}$).

This check looks for invalid names for a range of different identifiers.

You can set regular expressions to which the identifiers must conform if the defaults do not match your requirements.

If your project includes a Pylint configuration file, the settings contained in that file take precedence.

To find out more about Pylint, please refer to their site.

Loading history...
Coding Style Naming introduced by
The name y1 does not conform to the argument naming conventions ([a-z_][a-z0-9_]{2,30}$).

This check looks for invalid names for a range of different identifiers.

You can set regular expressions to which the identifiers must conform if the defaults do not match your requirements.

If your project includes a Pylint configuration file, the settings contained in that file take precedence.

To find out more about Pylint, please refer to their site.

Loading history...
Coding Style Naming introduced by
The name x2 does not conform to the argument naming conventions ([a-z_][a-z0-9_]{2,30}$).

This check looks for invalid names for a range of different identifiers.

You can set regular expressions to which the identifiers must conform if the defaults do not match your requirements.

If your project includes a Pylint configuration file, the settings contained in that file take precedence.

To find out more about Pylint, please refer to their site.

Loading history...
Coding Style Naming introduced by
The name y2 does not conform to the argument naming conventions ([a-z_][a-z0-9_]{2,30}$).

This check looks for invalid names for a range of different identifiers.

You can set regular expressions to which the identifiers must conform if the defaults do not match your requirements.

If your project includes a Pylint configuration file, the settings contained in that file take precedence.

To find out more about Pylint, please refer to their site.

Loading history...
307
    """
308
    Return a list of points in a bresenham line.
309
310
    Implementation hastily copied from RogueBasin.
311
312
    Returns:
313
        List[Tuple[int, int]]: A list of (x, y) points,
314
            including both the start and end-points.
315
    """
316
    points = []
317
    issteep = abs(y2-y1) > abs(x2-x1)
318
    if issteep:
319
        x1, y1 = y1, x1
320
        x2, y2 = y2, x2
321
    rev = False
322
    if x1 > x2:
323
        x1, x2 = x2, x1
324
        y1, y2 = y2, y1
325
        rev = True
326
    deltax = x2 - x1
327
    deltay = abs(y2-y1)
328
    error = int(deltax / 2)
329
    y = y1
0 ignored issues
show
Coding Style Naming introduced by
The name y does not conform to the variable naming conventions ([a-z_][a-z0-9_]{2,30}$).

This check looks for invalid names for a range of different identifiers.

You can set regular expressions to which the identifiers must conform if the defaults do not match your requirements.

If your project includes a Pylint configuration file, the settings contained in that file take precedence.

To find out more about Pylint, please refer to their site.

Loading history...
330
    ystep = None
331
    if y1 < y2:
332
        ystep = 1
333
    else:
334
        ystep = -1
335
    for x in range(x1, x2 + 1):
0 ignored issues
show
Coding Style Naming introduced by
The name x does not conform to the variable naming conventions ([a-z_][a-z0-9_]{2,30}$).

This check looks for invalid names for a range of different identifiers.

You can set regular expressions to which the identifiers must conform if the defaults do not match your requirements.

If your project includes a Pylint configuration file, the settings contained in that file take precedence.

To find out more about Pylint, please refer to their site.

Loading history...
336
        if issteep:
337
            points.append((y, x))
338
        else:
339
            points.append((x, y))
340
        error -= deltay
341
        if error < 0:
342
            y += ystep
0 ignored issues
show
Coding Style Naming introduced by
The name y does not conform to the variable naming conventions ([a-z_][a-z0-9_]{2,30}$).

This check looks for invalid names for a range of different identifiers.

You can set regular expressions to which the identifiers must conform if the defaults do not match your requirements.

If your project includes a Pylint configuration file, the settings contained in that file take precedence.

To find out more about Pylint, please refer to their site.

Loading history...
343
            error += deltax
344
    # Reverse the list if the coordinates were reversed
345
    if rev:
346
        points.reverse()
347
    return points
348
349
350
quickFOV = _style.backport(quick_fov)
0 ignored issues
show
Coding Style Naming introduced by
The name quickFOV does not conform to the constant naming conventions ((([A-Z_][A-Z0-9_]*)|(__.*__))$).

This check looks for invalid names for a range of different identifiers.

You can set regular expressions to which the identifiers must conform if the defaults do not match your requirements.

If your project includes a Pylint configuration file, the settings contained in that file take precedence.

To find out more about Pylint, please refer to their site.

Loading history...
351
AStar.getPath = _style.backport(AStar.get_path)
352