particle.py 43.8 KB
Newer Older
Ahmad Reza's avatar
Ahmad Reza committed
1
2
3
4
5
6
7
8
9
10
11
"""
.. module:: particle
   :platform: Unix, Windows
   :synopsis: This module provides the interfaces of the robotics particle

.. moduleauthor:: Ahmad Reza Cheraghi

TODO: Erase Memory

"""

Karol Actun's avatar
Karol Actun committed
12
import logging
Ahmad Reza's avatar
Ahmad Reza committed
13
from lib import csv_generator, matter
14
from lib.swarm_sim_header import *
Ahmad Reza's avatar
Ahmad Reza committed
15

Ahmad Reza's avatar
Ahmad Reza committed
16

Ahmad Reza's avatar
Ahmad Reza committed
17
class Particle(matter.Matter):
18
    """In the classe marker all the methods for the characterstic of a marker is included"""
Karol Actun's avatar
Karol Actun committed
19
20

    def __init__(self, world, coordinates, color, particle_counter=0):
21
        """Initializing the marker constructor"""
Karol Actun's avatar
Karol Actun committed
22
23
        super().__init__(world, coordinates, color,
                         type="particle", mm_size=world.config_data.particle_mm_size)
24
        self.number = particle_counter
Ahmad Reza's avatar
Ahmad Reza committed
25
26
27
28
        self.__isCarried = False
        self.carried_tile = None
        self.carried_particle = None
        self.steps = 0
Karol Actun's avatar
Karol Actun committed
29
        self.csv_particle_writer = csv_generator.CsvParticleData(self.get_id(), self.number)
Ahmad Reza's avatar
Ahmad Reza committed
30
31

    def has_tile(self):
Karol Actun's avatar
Karol Actun committed
32
        if self.carried_tile is None:
Ahmad Reza's avatar
Ahmad Reza committed
33
34
35
36
37
            return False
        else:
            return True

    def has_particle(self):
Karol Actun's avatar
Karol Actun committed
38
39
        if self.carried_particle is None:
            return False
Ahmad Reza's avatar
Ahmad Reza committed
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
        else:
            return True

    def get_carried_status(self):
        """
        Get the status if it is taken or not

        :return: Tiles status
        """
        return self.__isCarried

    def check_on_tile(self):
        """
        Checks if the particle is on a tile

        :return: True: On a tile; False: Not on a Tile
        """
57
        if self.coordinates in self.world.tile_map_coordinates:
Ahmad Reza's avatar
Ahmad Reza committed
58
59
60
61
62
63
64
65
66
67
            return True
        else:
            return False

    def check_on_particle(self):
        """
        Checks if the particle is on a particle

        :return: True: On a particle; False: Not on a particle
        """
68
        if self.coordinates in self.world.particle_map_coordinates:
Ahmad Reza's avatar
Ahmad Reza committed
69
70
71
72
            return True
        else:
            return False

73
    def check_on_marker(self):
Ahmad Reza's avatar
Ahmad Reza committed
74
        """
75
        Checks if the particle is on a marker
Ahmad Reza's avatar
Ahmad Reza committed
76

77
        :return: True: On a marker; False: Not on a marker
Ahmad Reza's avatar
Ahmad Reza committed
78
        """
79
        if self.coordinates in self.world.marker_map_coordinates:
Ahmad Reza's avatar
Ahmad Reza committed
80
81
82
83
            return True
        else:
            return False

84
    def move_to(self, direction):
Ahmad Reza's avatar
Ahmad Reza committed
85
        """
Karol Actun's avatar
Karol Actun committed
86
        Moves the particle to the given direction
Ahmad Reza's avatar
Ahmad Reza committed
87

Karol Actun's avatar
Karol Actun committed
88
        :param direction: The direction is defined by loaded grid class
Ahmad Reza's avatar
Ahmad Reza committed
89
90
        :return: True: Success Moving;  False: Non moving
        """
91
        direction_coord = get_coordinates_in_direction(self.coordinates, direction)
92
        direction, direction_coord = self.check_within_border(direction, direction_coord)
Karol Actun's avatar
Karol Actun committed
93
        if self.world.grid.is_valid_location(direction_coord):
Karol Actun's avatar
Karol Actun committed
94
95
96
            if direction_coord not in self.world.particle_map_coordinates:
                if self.coordinates in self.world.particle_map_coordinates:
                    del self.world.particle_map_coordinates[self.coordinates]
97
98
                self.coordinates = direction_coord
                self.world.particle_map_coordinates[self.coordinates] = self
Karol Actun's avatar
Karol Actun committed
99
                self.world.vis.particle_changed(self)
100
                logging.info("particle %s successfully moved to %s", str(self.get_id()), direction)
Karol Actun's avatar
Karol Actun committed
101
                self.world.csv_round.update_metrics(steps=1)
Ahmad Reza's avatar
Ahmad Reza committed
102
                self.csv_particle_writer.write_particle(steps=1)
Ahmad Reza Cheraghi's avatar
Ahmad Reza Cheraghi committed
103
                self.check_for_carried_tile_or_particle()
Ahmad Reza's avatar
Ahmad Reza committed
104
                return True
Karol Actun's avatar
Karol Actun committed
105

106
        return False
Ahmad Reza's avatar
Ahmad Reza committed
107

Ahmad Reza Cheraghi's avatar
Ahmad Reza Cheraghi committed
108
109
    def check_for_carried_tile_or_particle(self):
        if self.carried_tile is not None:
110
            self.carried_tile.coordinates = self.coordinates
Karol Actun's avatar
Karol Actun committed
111
            self.world.vis.tile_changed(self.carried_tile)
Ahmad Reza Cheraghi's avatar
Ahmad Reza Cheraghi committed
112
        elif self.carried_particle is not None:
113
            self.carried_particle.coordinates = self.coordinates
Karol Actun's avatar
Karol Actun committed
114
            self.world.vis.particle_changed(self.carried_particle)
Ahmad Reza Cheraghi's avatar
Ahmad Reza Cheraghi committed
115

116
    def check_within_border(self, direction, direction_coord):
Ahmad Reza's avatar
Ahmad Reza committed
117
        if self.world.config_data.border == 1 and \
Karol Actun's avatar
Karol Actun committed
118
119
                (abs(direction_coord[0]) > self.world.get_sim_x_size() or abs(
                    direction_coord[1]) > self.world.get_sim_y_size()):
120
            direction = direction - 3 if direction > 2 else direction + 3
121
            direction_coord = get_coordinates_in_direction(self.coordinates, direction)
122
        return direction, direction_coord
Ahmad Reza Cheraghi's avatar
Ahmad Reza Cheraghi committed
123

Karol Actun's avatar
Karol Actun committed
124
    def read_from_with(self, target, key=None):
Ahmad Reza's avatar
Ahmad Reza committed
125
        """
Karol Actun's avatar
Karol Actun committed
126
        Read the memories from the matters (particle, tile, or marker object) memories with a given keyword
Ahmad Reza's avatar
Ahmad Reza committed
127

Karol Actun's avatar
Karol Actun committed
128
        :param target: The matter can be either a particle, tile, or marker
Ahmad Reza's avatar
Ahmad Reza committed
129
130
131
        :param key: A string keyword to searcg for the data in the memory
        :return: The matters memory; None
        """
Karol Actun's avatar
Karol Actun committed
132
133
        if key is not None:
            tmp_memory = target.read_memory_with(key)
Ahmad Reza's avatar
Ahmad Reza committed
134
        else:
Karol Actun's avatar
Karol Actun committed
135
            tmp_memory = target.read_whole_memory()
Ahmad Reza's avatar
Ahmad Reza committed
136

Karol Actun's avatar
Karol Actun committed
137
138
139
140
        if tmp_memory is not None:
            if not (hasattr(tmp_memory, '__len__')) or len(tmp_memory) > 0:
                if target.type == "particle":
                    self.world.csv_round.update_metrics(particle_read=1)
141
                    self.csv_particle_writer.write_particle(particle_read=1)
Karol Actun's avatar
Karol Actun committed
142
143
                elif target.type == "tile":
                    self.world.csv_round.update_metrics(tile_read=1)
144
                    self.csv_particle_writer.write_particle(tile_read=1)
Karol Actun's avatar
Karol Actun committed
145
146
                elif target.type == "marker":
                    self.world.csv_round.update_metrics(marker_read=1)
147
148
149
                    self.csv_particle_writer.write_particle(marker_read=1)
                return tmp_memory
        return None
Ahmad Reza's avatar
Ahmad Reza committed
150

Karol Actun's avatar
Karol Actun committed
151
    def matter_in(self, direction):
Ahmad Reza Cheraghi's avatar
Ahmad Reza Cheraghi committed
152
        """
153
        :param direction: the directionection to check if a matter is there
Ahmad Reza Cheraghi's avatar
Ahmad Reza Cheraghi committed
154
155
        :return: True: if a matter is there, False: if not
        """
Karol Actun's avatar
Karol Actun committed
156
157
158
159
160
        if get_coordinates_in_direction(self.coordinates, direction) in self.world.get_tile_map_coordinates() \
                or get_coordinates_in_direction(self.coordinates, direction) \
                in self.world.get_particle_map_coordinates() \
                or get_coordinates_in_direction(self.coordinates, direction) \
                in self.world.get_marker_map_coordinates():
Ahmad Reza Cheraghi's avatar
Ahmad Reza Cheraghi committed
161
162
163
            return True
        else:
            return False
Ahmad Reza's avatar
Ahmad Reza committed
164

Karol Actun's avatar
Karol Actun committed
165
    def tile_in(self, direction):
Ahmad Reza Cheraghi's avatar
Ahmad Reza Cheraghi committed
166
        """
Karol Actun's avatar
Karol Actun committed
167
        :param direction: the direction to check if a tile is there
Ahmad Reza Cheraghi's avatar
Ahmad Reza Cheraghi committed
168
169
        :return: True: if a tile is there, False: if not
        """
170
        if get_coordinates_in_direction(self.coordinates, direction) in self.world.get_tile_map_coordinates():
Ahmad Reza Cheraghi's avatar
Ahmad Reza Cheraghi committed
171
172
173
            return True
        else:
            return False
Ahmad Reza's avatar
Ahmad Reza committed
174

Karol Actun's avatar
Karol Actun committed
175
    def particle_in(self, direction):
Ahmad Reza Cheraghi's avatar
Ahmad Reza Cheraghi committed
176
        """
Karol Actun's avatar
Karol Actun committed
177
        :param direction: the direction to check if a particle is there
Ahmad Reza Cheraghi's avatar
Ahmad Reza Cheraghi committed
178
179
        :return: True: if a particle is there, False: if not
        """
180
        if get_coordinates_in_direction(self.coordinates, direction) in self.world.get_particle_map_coordinates():
Ahmad Reza Cheraghi's avatar
Ahmad Reza Cheraghi committed
181
182
183
            return True
        else:
            return False
Ahmad Reza's avatar
Ahmad Reza committed
184

Karol Actun's avatar
Karol Actun committed
185
    def marker_in(self, direction):
Ahmad Reza Cheraghi's avatar
Ahmad Reza Cheraghi committed
186
        """
Karol Actun's avatar
Karol Actun committed
187
        :param direction: the direction to check if a marker is there
Ahmad Reza Cheraghi's avatar
Ahmad Reza Cheraghi committed
188
189
        :return: True: if a marker is there, False: if not
        """
190
        if get_coordinates_in_direction(self.coordinates, direction) in self.world.get_marker_map_coordinates():
Ahmad Reza Cheraghi's avatar
Ahmad Reza Cheraghi committed
191
192
193
            return True
        else:
            return False
Ahmad Reza's avatar
Ahmad Reza committed
194

Karol Actun's avatar
Karol Actun committed
195
    def get_matter_in(self, direction):
196
197
198
199
200
201
        if get_coordinates_in_direction(self.coordinates, direction) in self.world.get_tile_map_coordinates():
            return self.world.get_tile_map_coordinates()[get_coordinates_in_direction(self.coordinates, direction)]
        elif get_coordinates_in_direction(self.coordinates, direction) in self.world.get_particle_map_coordinates():
            return self.world.get_particle_map_coordinates()[get_coordinates_in_direction(self.coordinates, direction)]
        elif get_coordinates_in_direction(self.coordinates, direction) in self.world.get_marker_map_coordinates():
            return self.world.get_marker_map_coordinates()[get_coordinates_in_direction(self.coordinates, direction)]
Ahmad Reza Cheraghi's avatar
Ahmad Reza Cheraghi committed
202
203
        else:
            return False
Ahmad Reza's avatar
Ahmad Reza committed
204

Karol Actun's avatar
Karol Actun committed
205
    def get_tile_in(self, direction):
206
207
        if get_coordinates_in_direction(self.coordinates, direction) in self.world.get_tile_map_coordinates():
            return self.world.get_tile_map_coordinates()[get_coordinates_in_direction(self.coordinates, direction)]
Ahmad Reza Cheraghi's avatar
Ahmad Reza Cheraghi committed
208
209
        else:
            return False
Ahmad Reza's avatar
Ahmad Reza committed
210

Karol Actun's avatar
Karol Actun committed
211
    def get_particle_in(self, direction):
212
213
        if get_coordinates_in_direction(self.coordinates, direction) in self.world.get_particle_map_coordinates():
            return self.world.get_particle_map_coordinates()[get_coordinates_in_direction(self.coordinates, direction)]
Ahmad Reza Cheraghi's avatar
Ahmad Reza Cheraghi committed
214
215
        else:
            return False
Ahmad Reza's avatar
Ahmad Reza committed
216

Karol Actun's avatar
Karol Actun committed
217
    def get_marker_in(self, direction):
218
219
        if get_coordinates_in_direction(self.coordinates, direction) in self.world.get_marker_map_coordinates():
            return self.world.get_marker_map_coordinates()[get_coordinates_in_direction(self.coordinates, direction)]
Ahmad Reza Cheraghi's avatar
Ahmad Reza Cheraghi committed
220
221
        else:
            return False
Ahmad Reza's avatar
Ahmad Reza committed
222

223
    def get_marker(self):
224
225
        if self.coordinates in self.world.marker_map_coordinates:
            return self.world.get_marker_map_coordinates()[self.coordinates]
Ahmad Reza Cheraghi's avatar
Ahmad Reza Cheraghi committed
226
227
        else:
            return False
Ahmad Reza's avatar
Ahmad Reza committed
228

Ahmad Reza Cheraghi's avatar
Ahmad Reza Cheraghi committed
229
    def get_tile(self):
Karol Actun's avatar
Karol Actun committed
230
        if self.coordinates in self.world.get_tile_map_coordinates():
231
            return self.world.get_tile_map_coordinates()[self.coordinates]
Ahmad Reza Cheraghi's avatar
Ahmad Reza Cheraghi committed
232
233
        else:
            return False
Ahmad Reza's avatar
Ahmad Reza committed
234

Karol Actun's avatar
Karol Actun committed
235
    def write_to_with(self, target, key=None, data=None):
Ahmad Reza's avatar
Ahmad Reza committed
236
        """
Karol Actun's avatar
Karol Actun committed
237
        Writes data with given a keyword direction on the matters (particle, tile, or marker object) memory
Ahmad Reza's avatar
Ahmad Reza committed
238

Karol Actun's avatar
Karol Actun committed
239
        :param target: The matter can be either a particle, tile, or marker
Ahmad Reza's avatar
Ahmad Reza committed
240
241
242
243
        :param key: A string keyword so to order the data that is written into the memory
        :param data: The data that should be stored into the memory
        :return: True: Successful written into the memory; False: Unsuccessful
        """
Karol Actun's avatar
Karol Actun committed
244
245
246
        if data is not None:
            if key is None:
                wrote = target.write_memory(data)
Ahmad Reza's avatar
Ahmad Reza committed
247
            else:
Karol Actun's avatar
Karol Actun committed
248
249
250
251
                wrote = target.write_memory_with(key, data)
            if wrote:
                if target.type == "particle":
                    self.world.csv_round.update_metrics(particle_write=1)
Ahmad Reza's avatar
Ahmad Reza committed
252
                    self.csv_particle_writer.write_particle(particle_write=1)
Karol Actun's avatar
Karol Actun committed
253
254
                elif target.type == "tile":
                    self.world.csv_round.update_metrics(tile_write=1)
Ahmad Reza's avatar
Ahmad Reza committed
255
                    self.csv_particle_writer.write_particle(tile_write=1)
Karol Actun's avatar
Karol Actun committed
256
257
                elif target.type == "marker":
                    self.world.csv_round.update_metrics(marker_write=1)
258
                    self.csv_particle_writer.write_particle(marker_write=1)
Ahmad Reza's avatar
Ahmad Reza committed
259
260
261
262
263
264
                return True
            else:
                return False
        else:
            return False

Karol Actun's avatar
Karol Actun committed
265
    def scan_for_matters_within(self, matter_type='all', hop=1):
Ahmad Reza's avatar
Ahmad Reza committed
266
        """
267
        Scans for particles, tiles, or marker on a given hop distance and all the matters within the hop distance
Ahmad Reza's avatar
Ahmad Reza committed
268
269
270

        :todo: If nothing then everything should be scanned

Karol Actun's avatar
Karol Actun committed
271
272
        :param matter_type: For what matter this method should scan for.
                            Can be either particles, tiles, markers, or (default) all
Ahmad Reza's avatar
Ahmad Reza committed
273
274
275
276
        :param hop: The hop distance from the actual position of the scanning particle
        :return: A list of the founded matters
        """

Ahmad Reza's avatar
Ahmad Reza committed
277
        within_hop_list = []
Ahmad Reza's avatar
Ahmad Reza committed
278
        for i in range(1, hop + 1):
Karol Actun's avatar
Karol Actun committed
279
            in_list = self.scan_for_matters_in(matter_type, i)
Ahmad Reza's avatar
Ahmad Reza committed
280
281
282
283
            if in_list is not None:
                within_hop_list.extend(in_list)
        if len(within_hop_list) != 0:
            return within_hop_list
Ahmad Reza's avatar
Ahmad Reza committed
284
285
286
        else:
            return None

Karol Actun's avatar
Karol Actun committed
287
    def scan_for_matters_in(self, matter_type='all', hop=1):
Ahmad Reza's avatar
Ahmad Reza committed
288
        """
Ahmad Reza's avatar
Ahmad Reza committed
289
         Scanning for particles, tiles, or marker on a given hop distance
Ahmad Reza's avatar
Ahmad Reza committed
290

Karol Actun's avatar
Karol Actun committed
291
292
         :param matter_type: For what matter this method should scan for.
                             Can be either particles, tiles, markers, or (default) all
Ahmad Reza's avatar
Ahmad Reza committed
293
294
295
         :param hop: The hop distance from thee actual position of the scanning particle
         :return: A list of the founded matters
         """
Karol Actun's avatar
Karol Actun committed
296
297
298
299
300
301
302
303
304

        logging.info("particle on %s is scanning for %s in %i hops", str(self.coordinates), matter_type, hop)

        if matter_type == "particles":
            scanned_list = scan_in(self.world.particle_map_coordinates, self.coordinates, hop, self.world.grid)
        elif matter_type == "tiles":
            scanned_list = scan_in(self.world.tile_map_coordinates, self.coordinates, hop, self.world.grid)
        elif matter_type == "markers":
            scanned_list = scan_in(self.world.marker_map_coordinates, self.coordinates, hop, self.world.grid)
Ahmad Reza's avatar
Ahmad Reza committed
305
        else:
Karol Actun's avatar
Karol Actun committed
306
307
308
309
            scanned_list = scan_in(self.world.particle_map_coordinates, self.coordinates, hop, self.world.grid)
            scanned_list.extend(scan_in(self.world.tile_map_coordinates, self.coordinates, hop, self.world.grid))
            scanned_list.extend(scan_in(self.world.marker_map_coordinates, self.coordinates, hop, self.world.grid))
        return scanned_list
Ahmad Reza's avatar
Ahmad Reza committed
310

Ahmad Reza's avatar
Ahmad Reza committed
311
    def scan_for_particles_within(self, hop=1):
Ahmad Reza's avatar
Ahmad Reza committed
312
        """
313
        Scans for particles, tiles, or marker on a given hop distance and all the matters within the hop distance
Ahmad Reza's avatar
Ahmad Reza committed
314
315
316
317
318
319

        :todo: If nothing then everything should be scanned

        :param hop: The hop distance from the actual position of the scanning particle
        :return: A list of the founded matters
        """
Karol Actun's avatar
Karol Actun committed
320
        return scan_within(self.world.particle_map_coordinates, self.coordinates, hop, self.world.grid)
Ahmad Reza's avatar
Ahmad Reza committed
321

Ahmad Reza's avatar
Ahmad Reza committed
322
    def scan_for_particles_in(self, hop=1):
Ahmad Reza's avatar
Ahmad Reza committed
323
        """
324
        Scanning for particles, tiles, or marker on a given hop distance
Ahmad Reza's avatar
Ahmad Reza committed
325
326
327
328
329

        :param hop: The hop distance from thee actual position of the scanning particle
        :return: A list of the founded matters
        """

Karol Actun's avatar
Karol Actun committed
330
        return scan_in(self.world.particle_map_coordinates, self.coordinates, hop, self.world.grid)
Ahmad Reza's avatar
Ahmad Reza committed
331

Karol Actun's avatar
Karol Actun committed
332
    def scan_for_tiles_within(self, hop=1):
Ahmad Reza's avatar
Ahmad Reza committed
333
        """
334
        Scans for particles, tiles, or marker on a given hop distance and all the matters within the hop distance
Ahmad Reza's avatar
Ahmad Reza committed
335
336
337
338
339
340
341

        :todo: If nothing then everything should be scanned

        :param hop: The hop distance from the actual position of the scanning particle
        :return: A list of the founded matters
        """

Karol Actun's avatar
Karol Actun committed
342
        return scan_within(self.world.tile_map_coordinates, self.coordinates, hop, self.world.grid)
Ahmad Reza's avatar
Ahmad Reza committed
343

Ahmad Reza's avatar
Ahmad Reza committed
344
    def scan_for_tiles_in(self, hop=1):
Ahmad Reza's avatar
Ahmad Reza committed
345
        """
346
        Scanning for particles, tiles, or marker on a given hop distance
Ahmad Reza's avatar
Ahmad Reza committed
347
348
349
350

        :param hop: The hop distance from thee actual position of the scanning particle
        :return: A list of the founded matters
        """
Karol Actun's avatar
Karol Actun committed
351
        return scan_in(self.world.tile_map_coordinates, self.coordinates, hop, self.world.grid)
Ahmad Reza's avatar
Ahmad Reza committed
352

Ahmad Reza's avatar
Ahmad Reza committed
353
    def scan_for_markers_within(self, hop=1):
Ahmad Reza's avatar
Ahmad Reza committed
354
        """
355
        Scans for particles, tiles, or marker on a given hop distance and all the matters within the hop distance
Ahmad Reza's avatar
Ahmad Reza committed
356
357
358
359
360
361
362

        :todo: If nothing then everything should be scanned

        :param hop: The hop distance from the actual position of the scanning particle
        :return: A list of the founded matters
        """

Karol Actun's avatar
Karol Actun committed
363
        return scan_within(self.world.marker_map_coordinates, self.coordinates, hop, self.world.grid)
Ahmad Reza's avatar
Ahmad Reza committed
364

Ahmad Reza's avatar
Ahmad Reza committed
365
    def scan_for_markers_in(self, hop=1):
Ahmad Reza's avatar
Ahmad Reza committed
366
        """
367
        Scanning for particles, tiles, or marker on a given hop distance
Ahmad Reza's avatar
Ahmad Reza committed
368
369
370
371

        :param hop: The hop distance from thee actual position of the scanning particle
        :return: A list of the founded matters
        """
Karol Actun's avatar
Karol Actun committed
372
        return scan_in(self.world.marker_map_coordinates, self.coordinates, hop, self.world.grid)
Ahmad Reza's avatar
Ahmad Reza committed
373

Karol Actun's avatar
Karol Actun committed
374
    def take_me(self, coordinates):
Ahmad Reza's avatar
Ahmad Reza committed
375
376
377
        """
        The particle is getting taken from the the other particle on the given coordinate

Karol Actun's avatar
Karol Actun committed
378
        :param coordinates, the coordinates of the particle which takes this particle
Ahmad Reza's avatar
Ahmad Reza committed
379
380
381
382
        :return: True: Successful taken; False: Cannot be taken or wrong Coordinates
        """

        if not self.__isCarried:
383
384
            if self.coordinates in self.world.particle_map_coordinates:
                del self.world.particle_map_coordinates[self.coordinates]
Ahmad Reza's avatar
Ahmad Reza committed
385
            self.__isCarried = True
386
            self.coordinates = coordinates
Karol Actun's avatar
Karol Actun committed
387
            self.world.vis.particle_changed(self)
Ahmad Reza's avatar
Ahmad Reza committed
388
389
390
391
            return True
        else:
            return False

392
    def drop_me(self, coordinates):
Ahmad Reza's avatar
Ahmad Reza committed
393
394
395
        """
        The actual particle is getting dropped

396
        :param coordinates: the given position
Ahmad Reza's avatar
Ahmad Reza committed
397
398
        :return: None
        """
399
        self.coordinates = coordinates
Karol Actun's avatar
Karol Actun committed
400
        self.world.particle_map_coordinates[coordinates] = self
Ahmad Reza's avatar
Ahmad Reza committed
401
        self.__isCarried = False
Karol Actun's avatar
Karol Actun committed
402
        self.world.vis.particle_changed(self)
Ahmad Reza's avatar
Ahmad Reza committed
403

Karol Actun's avatar
Karol Actun committed
404
    def create_tile(self):
Ahmad Reza's avatar
Ahmad Reza committed
405
406
407
        """
        Creates a tile on the particles actual position

Ahmad Reza's avatar
Ahmad Reza committed
408
        :return: New Tile or False
Ahmad Reza's avatar
Ahmad Reza committed
409
        """
410
        logging.info("Going to create a tile on position %s", str(self.coordinates))
Karol Actun's avatar
Karol Actun committed
411
        new_tile = self.world.add_tile(self.coordinates)
Ahmad Reza's avatar
Ahmad Reza committed
412
        if new_tile:
Karol Actun's avatar
Karol Actun committed
413
            self.world.tile_map_coordinates[self.coordinates].created = True
Ahmad Reza's avatar
Ahmad Reza committed
414
            self.csv_particle_writer.write_particle(tile_created=1)
Ahmad Reza's avatar
Ahmad Reza committed
415
            self.world.csv_round.update_tiles_num(len(self.world.get_tiles_list()))
Karol Actun's avatar
Karol Actun committed
416
            self.world.csv_round.update_metrics(tile_created=1)
Ahmad Reza's avatar
Ahmad Reza committed
417
418
419
            return new_tile
        else:
            return False
Ahmad Reza's avatar
Ahmad Reza committed
420

Karol Actun's avatar
Karol Actun committed
421
    def create_tile_in(self, direction=None):
Ahmad Reza's avatar
Ahmad Reza committed
422
        """
Karol Actun's avatar
Karol Actun committed
423
        Creates a tile either in a given direction
Ahmad Reza's avatar
Ahmad Reza committed
424

Karol Actun's avatar
Karol Actun committed
425
        :param direction: The direction on which the tile should be created.
Ahmad Reza's avatar
Ahmad Reza committed
426
        :return: New tile or False
Ahmad Reza's avatar
Ahmad Reza committed
427
        """
Karol Actun's avatar
Karol Actun committed
428
429
        logging.info("particle with id %s is" % self.get_id())
        logging.info("Going to create a tile in %s " % str(direction))
Karol Actun's avatar
Karol Actun committed
430
        if direction is not None:
431
            coordinates = get_coordinates_in_direction(self.coordinates, direction)
Karol Actun's avatar
Karol Actun committed
432
            new_tile = self.world.add_tile(coordinates)
Ahmad Reza's avatar
Ahmad Reza committed
433
            if new_tile:
Karol Actun's avatar
Karol Actun committed
434
                self.world.tile_map_coordinates[coordinates].created = True
Ahmad Reza's avatar
Ahmad Reza committed
435
                logging.info("Tile is created")
Ahmad Reza's avatar
Ahmad Reza committed
436
                self.world.new_tile_flag = True
Ahmad Reza's avatar
Ahmad Reza committed
437
                self.csv_particle_writer.write_particle(tile_created=1)
Ahmad Reza's avatar
Ahmad Reza committed
438
                self.world.csv_round.update_tiles_num(len(self.world.get_tiles_list()))
Karol Actun's avatar
Karol Actun committed
439
                self.world.csv_round.update_metrics(tile_created=1)
Ahmad Reza's avatar
Ahmad Reza committed
440
441
442
                return new_tile
            else:
                return False
Ahmad Reza's avatar
Ahmad Reza committed
443
444
        else:
            logging.info("Not created tile ")
Ahmad Reza's avatar
Ahmad Reza committed
445
            return False
Ahmad Reza's avatar
Ahmad Reza committed
446

Karol Actun's avatar
Karol Actun committed
447
    def create_tile_on(self, coordinates=None):
Ahmad Reza's avatar
Ahmad Reza committed
448
449
450
        """
        Creates a tile either on a given x,y coordinates

Karol Actun's avatar
Karol Actun committed
451
        :param coordinates: the coordinates
Ahmad Reza's avatar
Ahmad Reza committed
452
        :return: New Tile or False
Ahmad Reza's avatar
Ahmad Reza committed
453
454
455
        """

        logging.info("particle with id %s is", self.get_id())
Karol Actun's avatar
Karol Actun committed
456
        if coordinates is not None:
Karol Actun's avatar
Karol Actun committed
457
458
459
            if self.world.grid.is_valid_location(coordinates):
                logging.info("Going to create a tile on position %s" % str(coordinates))
                if self.world.add_tile(coordinates):
Karol Actun's avatar
Karol Actun committed
460
                    self.world.tile_map_coordinates[coordinates, coordinates[1]].created = True
Ahmad Reza's avatar
Ahmad Reza committed
461
                    self.world.new_tile_flag = True
Ahmad Reza's avatar
Ahmad Reza committed
462
                    self.csv_particle_writer.write_particle(tile_created=1)
Karol Actun's avatar
Karol Actun committed
463
464
                    self.world.csv_round.update_tiles_num(len(self.world.get_tiles_list()))
                    self.world.csv_round.update_metrics(tile_created=1)
Ahmad Reza's avatar
Ahmad Reza committed
465
466
                    return True
                else:
Karol Actun's avatar
Karol Actun committed
467
                    logging.info("Not created tile on coordinates %s" % str(coordinates))
Ahmad Reza's avatar
Ahmad Reza committed
468
469
                    return False
            else:
Karol Actun's avatar
Karol Actun committed
470
                logging.info("Not created tile on coordinates %s" % str(coordinates))
Ahmad Reza's avatar
Ahmad Reza committed
471
                return False
Ahmad Reza's avatar
Ahmad Reza committed
472
473
474
475
476
477
478

    def delete_tile(self):
        """
        Deletes a tile on current position

        :return: True: Deleting successful; False: Deleting unsuccessful
        """
Karol Actun's avatar
Karol Actun committed
479
        logging.info("Particle %s is" % self.get_id())
Ahmad Reza's avatar
Ahmad Reza committed
480
        logging.info("is going to delete a tile on current position")
481
482
        if self.coordinates in self.world.get_tile_map_coordinates():
            if self.world.remove_tile_on(self.coordinates):
Ahmad Reza's avatar
Ahmad Reza committed
483
484
485
486
487
488
                self.csv_particle_writer.write_particle(tile_deleted=1)
                return True
        else:
            logging.info("Could not delet tile")
            return False

Karol Actun's avatar
Karol Actun committed
489
    def delete_tile_with(self, tile_id):
Ahmad Reza's avatar
Ahmad Reza committed
490
491
492
493
494
495
        """
        Deletes a tile with a given tile-id

        :param tile_id: The id of the tile that should be deleted
        :return: True: Deleting successful; False: Deleting unsuccessful
        """
Karol Actun's avatar
Karol Actun committed
496
497
498
        logging.info("Particle %s is" % self.get_id())
        logging.info("is going to delete a tile with tile id %s" % str(tile_id))
        if self.world.remove_tile(tile_id):
Ahmad Reza's avatar
Ahmad Reza committed
499
500
501
            self.csv_particle_writer.write_particle(tile_deleted=1)
            return True
        else:
Karol Actun's avatar
Karol Actun committed
502
            logging.info("Could not delet tile with tile id %s" % str(tile_id))
Ahmad Reza's avatar
Ahmad Reza committed
503
504
            return False

505
    def delete_tile_in(self, direction=None):
Ahmad Reza's avatar
Ahmad Reza committed
506
        """
507
        Deletes a tile either in a given directionection
Ahmad Reza's avatar
Ahmad Reza committed
508

509
        :param direction: The directionection on which the tile should be deleted. Options: E, SE, SW, W, NW, NE,
Ahmad Reza's avatar
Ahmad Reza committed
510
511
512

        :return: True: Deleting successful; False: Deleting unsuccessful
        """
513
        coordinates = ()
514
        if direction is not None:
515
            coordinates = get_coordinates_in_direction(self.coordinates, direction)
Karol Actun's avatar
Karol Actun committed
516
            logging.info("Deleting tile in %s directionection" % str(direction))
517
518
            if coordinates is not None:
                if self.world.remove_tile_on(coordinates):
Karol Actun's avatar
Karol Actun committed
519
                    logging.info("Deleted tile with tile on coordinates %s" % str(coordinates))
Ahmad Reza's avatar
Ahmad Reza committed
520
521
522
                    self.csv_particle_writer.write_particle(tile_deleted=1)
                    return True
                else:
Karol Actun's avatar
Karol Actun committed
523
                    logging.info("Could not delet tile on coordinates %s" % str(coordinates))
Ahmad Reza's avatar
Ahmad Reza committed
524
525
                    return False
        else:
Karol Actun's avatar
Karol Actun committed
526
            logging.info("Could not delet tile on coordinates %s" % str(coordinates))
Ahmad Reza's avatar
Ahmad Reza committed
527
528
529
530
531
532
533
534
535
536
            return False

    def delete_tile_on(self, x=None, y=None):
        """
        Deletes a tile either on a given x,y coordinates
,
        :param x: x coordinate
        :param y: y coordinate
        :return: True: Deleting successful; False: Deleting unsuccessful
        """
537
        coordinates = ()
Ahmad Reza's avatar
Ahmad Reza committed
538
        if x is not None and y is not None:
539
540
            coordinates = (x, y)
            if self.world.remove_tile_on(coordinates):
Karol Actun's avatar
Karol Actun committed
541
                logging.info("Deleted tile with tile on coordinates %s" % str(coordinates))
Ahmad Reza's avatar
Ahmad Reza committed
542
543
544
                self.csv_particle_writer.write_particle(tile_deleted=1)
                return True
            else:
Karol Actun's avatar
Karol Actun committed
545
                logging.info("Could not delet tile on coordinates %s" % str(coordinates))
Ahmad Reza's avatar
Ahmad Reza committed
546
547
                return False
        else:
Karol Actun's avatar
Karol Actun committed
548
            logging.info("Could not delet tile on coordinates %s" % str(coordinates))
Ahmad Reza's avatar
Ahmad Reza committed
549
550
            return False

Karol Actun's avatar
Karol Actun committed
551
    def take_tile_with(self, tile_id):
Ahmad Reza's avatar
Ahmad Reza committed
552
        """
Karol Actun's avatar
Karol Actun committed
553
        Takes a tile with a given tile id
Ahmad Reza's avatar
Ahmad Reza committed
554

Karol Actun's avatar
Karol Actun committed
555
        :param tile_id:  The id of the tile that should be taken
Ahmad Reza's avatar
Ahmad Reza committed
556
557
558
        :return: True: successful taken; False: unsuccessful taken
        """
        if self.carried_particle is None and self.carried_tile is None:
Karol Actun's avatar
Karol Actun committed
559
560
561
562
563
564
565
            if tile_id in self.world.tile_map_id:
                self.carried_tile = self.world.tile_map_id[tile_id]
                if self.carried_tile.take():
                    logging.info("Tile with tile id %s  has been taken", str(tile_id))
                    self.carried_tile.coordinates = self.coordinates
                    self.world.vis.tile_changed(self.carried_tile)
                    self.world.csv_round.update_metrics(tiles_taken=1)
Ahmad Reza's avatar
Ahmad Reza committed
566
567
568
                    self.csv_particle_writer.write_particle(tiles_taken=1)
                    return True
                else:
Karol Actun's avatar
Karol Actun committed
569
570
                    self.carried_tile = None
                    logging.info("Tile with tile id %s could not be taken" % str(tile_id))
Ahmad Reza's avatar
Ahmad Reza committed
571
572
                    return False
            else:
Karol Actun's avatar
Karol Actun committed
573
                logging.info("Tile with tile id %s is not in the world" % str(tile_id))
Ahmad Reza's avatar
Ahmad Reza committed
574
575
                return False
        else:
Karol Actun's avatar
Karol Actun committed
576
577
578

            logging.info("Tile cannot taken because particle is carrying either a tile or a particle (%s, %s)"
                         % (str(self.carried_tile), str(self.carried_particle)))
Ahmad Reza's avatar
Ahmad Reza committed
579
580
            return False

Karol Actun's avatar
Karol Actun committed
581
    def take_tile_in(self, direction):
Ahmad Reza's avatar
Ahmad Reza committed
582
        """
Karol Actun's avatar
Karol Actun committed
583
        Takes a tile that is in a given direction
Ahmad Reza's avatar
Ahmad Reza committed
584

Karol Actun's avatar
Karol Actun committed
585
        :param direction: The direction on which the tile should be taken.
Ahmad Reza's avatar
Ahmad Reza committed
586
587
        :return: True: successful taken; False: unsuccessful taken
        """
Karol Actun's avatar
Karol Actun committed
588
589
        coordinates = get_coordinates_in_direction(self.coordinates, direction)
        return self.take_tile_on(coordinates)
Ahmad Reza's avatar
Ahmad Reza committed
590

Karol Actun's avatar
Karol Actun committed
591
    def take_tile_on(self, coordinates):
Ahmad Reza's avatar
Ahmad Reza committed
592
        """
Karol Actun's avatar
Karol Actun committed
593
        Takes a tile on given coordinates
Ahmad Reza's avatar
Ahmad Reza committed
594

Karol Actun's avatar
Karol Actun committed
595
        :param coordinates of the tile
Ahmad Reza's avatar
Ahmad Reza committed
596
597
        :return: True: successful taken; False: unsuccessful taken
        """
Karol Actun's avatar
Karol Actun committed
598
        if self.world.grid.is_valid_location(coordinates):
599
            if coordinates in self.world.tile_map_coordinates:
Karol Actun's avatar
Karol Actun committed
600
                return self.take_tile_with(self.world.tile_map_coordinates[coordinates].get_id())
Ahmad Reza's avatar
Ahmad Reza committed
601
            else:
Karol Actun's avatar
Karol Actun committed
602
                logging.info("There is no Tile at %s" % str(coordinates))
Ahmad Reza's avatar
Ahmad Reza committed
603
604
                return False
        else:
Karol Actun's avatar
Karol Actun committed
605
            logging.info("invalid coordinates %s" % str(coordinates))
Ahmad Reza's avatar
Ahmad Reza committed
606
607
            return False

Karol Actun's avatar
Karol Actun committed
608
    def take_tile(self):
Ahmad Reza's avatar
Ahmad Reza committed
609
        """
Karol Actun's avatar
Karol Actun committed
610
        Takes a tile on the actual position
Ahmad Reza's avatar
Ahmad Reza committed
611
612
613

        :return: True: successful taken; False: unsuccessful taken
        """
Karol Actun's avatar
Karol Actun committed
614
        return self.take_tile_on(self.coordinates)
Ahmad Reza's avatar
Ahmad Reza committed
615
616
617
618
619
620
621

    def drop_tile(self):
        """
        Drops the taken tile on the particles actual position

        :return: None
        """
Karol Actun's avatar
Karol Actun committed
622
        return self.drop_tile_on(self.coordinates)
Ahmad Reza's avatar
Ahmad Reza committed
623

624
    def drop_tile_in(self, direction):
Ahmad Reza's avatar
Ahmad Reza committed
625
        """
Karol Actun's avatar
Karol Actun committed
626
        Drops the taken tile on a given direction
Ahmad Reza's avatar
Ahmad Reza committed
627

628
         :param direction: The directionection on which the tile should be dropped. Options: E, SE, SW, W, NW, NE,
Ahmad Reza's avatar
Ahmad Reza committed
629
        """
Karol Actun's avatar
Karol Actun committed
630
        return self.drop_tile_on(get_coordinates_in_direction(self.coordinates, direction))
Ahmad Reza's avatar
Ahmad Reza committed
631

Karol Actun's avatar
Karol Actun committed
632
    def drop_tile_on(self, coordinates):
Ahmad Reza's avatar
Ahmad Reza committed
633
        """
Karol Actun's avatar
Karol Actun committed
634
        Drops the taken tile on a given direction
Ahmad Reza's avatar
Ahmad Reza committed
635

Karol Actun's avatar
Karol Actun committed
636
        :param coordinates
Ahmad Reza's avatar
Ahmad Reza committed
637
638
        """
        if self.carried_tile is not None:
Karol Actun's avatar
Karol Actun committed
639
            if self.world.grid.is_valid_location(coordinates):
640
                if coordinates not in self.world.get_tile_map_coordinates():
Ahmad Reza's avatar
Ahmad Reza committed
641
                    try:  # cher: insert so to overcome the AttributeError
642
                        self.carried_tile.drop_me(coordinates)
Ahmad Reza's avatar
Ahmad Reza committed
643
644
645
                    except AttributeError:
                        pass
                    self.carried_tile = None
Karol Actun's avatar
Karol Actun committed
646
                    self.world.csv_round.update_metrics(tiles_dropped=1)
Ahmad Reza's avatar
Ahmad Reza committed
647
                    self.csv_particle_writer.write_particle(tiles_dropped=1)
648
                    logging.info("Dropped tile on %s coordinate", str(coordinates))
Ahmad Reza's avatar
Ahmad Reza committed
649
650
651
652
653
654
655
656
657
658
659
                    return True
                else:
                    logging.info("Is not possible to drop the tile on that position because it is occupied")
                    return False
            else:
                logging.info("Wrong coordinates for dropping the tile")
                return False
        else:
            logging.info("No tile is taken for dropping")
            return False

Karol Actun's avatar
Karol Actun committed
660
    def create_particle(self):
Ahmad Reza's avatar
Ahmad Reza committed
661
662
663
        """
        Creates a particle on the particles actual position

Ahmad Reza's avatar
Ahmad Reza committed
664
        :return: New Particle or False
Ahmad Reza's avatar
Ahmad Reza committed
665
        """
666
        logging.info("Going to create on position %s", str(self.coordinates))
Karol Actun's avatar
Karol Actun committed
667
        new_particle = self.world.add_particle(self.coordinates)
Ahmad Reza's avatar
Ahmad Reza committed
668
        if new_particle:
Karol Actun's avatar
Karol Actun committed
669
            self.world.particle_map_coordinates[self.coordinates[0], self.coordinates[1]].created = True
Ahmad Reza's avatar
Ahmad Reza committed
670
            self.csv_particle_writer.write_particle(particle_created=1)
Ahmad Reza's avatar
Ahmad Reza committed
671
            self.world.csv_round.update_particle_num(len(self.world.get_particle_list()))
Karol Actun's avatar
Karol Actun committed
672
            self.world.csv_round.update_metrics(particle_created=1)
Ahmad Reza's avatar
Ahmad Reza committed
673
674
675
            return new_particle
        else:
            return False
Ahmad Reza's avatar
Ahmad Reza committed
676

Karol Actun's avatar
Karol Actun committed
677
    def create_particle_in(self, direction=None):
Ahmad Reza's avatar
Ahmad Reza committed
678
        """
Karol Actun's avatar
Karol Actun committed
679
        Creates a particle either in a given direction
Ahmad Reza's avatar
Ahmad Reza committed
680

Karol Actun's avatar
Karol Actun committed
681
        :toDo: separate the direction and coordinates and delete state
Ahmad Reza's avatar
Ahmad Reza committed
682

Karol Actun's avatar
Karol Actun committed
683
        :param direction: The direction on which the particle should be created. Options: E, SE, SW, W, NW, NE,
Ahmad Reza's avatar
Ahmad Reza committed
684
        :return: New Particle or False
Ahmad Reza's avatar
Ahmad Reza committed
685
        """
686
        if direction is not None:
687
688
            coordinates = get_coordinates_in_direction(self.coordinates, direction)
            logging.info("Going to create a particle in %s on position %s", str(direction), str(coordinates))
Karol Actun's avatar
Karol Actun committed
689
            new_particle = self.world.add_particle(coordinates)
Ahmad Reza's avatar
Ahmad Reza committed
690
            if new_particle:
Karol Actun's avatar
Karol Actun committed
691
                self.world.particle_map_coordinates[coordinates].created = True
692
                logging.info("Created particle on coordinates %s", coordinates)
Ahmad Reza's avatar
Ahmad Reza committed
693
                self.world.csv_round.update_particle_num(len(self.world.get_particle_list()))
Karol Actun's avatar
Karol Actun committed
694
                self.world.csv_round.update_metrics(particle_created=1)
Ahmad Reza's avatar
Ahmad Reza committed
695
                self.csv_particle_writer.write_particle(particle_created=1)
Ahmad Reza's avatar
Ahmad Reza committed
696
697
698
                return new_particle
            else:
                return False
Ahmad Reza's avatar
Ahmad Reza committed
699
        else:
Karol Actun's avatar
Karol Actun committed
700
            logging.info("Particle not created. invalid direction (None)")
Ahmad Reza's avatar
Ahmad Reza committed
701
            return False
Ahmad Reza's avatar
Ahmad Reza committed
702

Karol Actun's avatar
Karol Actun committed
703
    def create_particle_on(self, coordinates):
Ahmad Reza's avatar
Ahmad Reza committed
704
        """
Karol Actun's avatar
Karol Actun committed
705
        Creates a particle either on the given coordinates
Ahmad Reza's avatar
Ahmad Reza committed
706

Karol Actun's avatar
Karol Actun committed
707
        :toDo: separate the direction and coordinates and delete state
Ahmad Reza's avatar
Ahmad Reza committed
708

Karol Actun's avatar
Karol Actun committed
709
        :param coordinates: the coordinates
Ahmad Reza's avatar
Ahmad Reza committed
710
        :return: New Particle or False
Ahmad Reza's avatar
Ahmad Reza committed
711
        """
Karol Actun's avatar
Karol Actun committed
712
713
714
715
        if coordinates is not None:
            if self.world.grid.is_valid_location(coordinates):
                logging.info("Going to create a particle on position %s" % str(coordinates))
                new_particle = self.world.add_particle(coordinates)
Ahmad Reza's avatar
Ahmad Reza committed
716
                if new_particle:
717
                    self.world.particle_map_coordinates[coordinates[0], coordinates[1]].created = True
Karol Actun's avatar
Karol Actun committed
718
                    logging.info("Created particle on coordinates %s" % str(coordinates))
Ahmad Reza's avatar
Ahmad Reza committed
719
                    self.world.csv_round.update_particle_num(len(self.world.get_particle_list()))
Karol Actun's avatar
Karol Actun committed
720
                    self.world.csv_round.update_metrics(particle_created=1)
Ahmad Reza's avatar
Ahmad Reza committed
721
                    self.csv_particle_writer.write_particle(particle_created=1)
Ahmad Reza's avatar
Ahmad Reza committed
722
                    return new_particle
Ahmad Reza's avatar
Ahmad Reza committed
723
724
725
726
727
                else:
                    return False
            else:
                return False
        else:
Karol Actun's avatar
Karol Actun committed
728
            logging.info("Not created particle on coordinates %s" % str(coordinates))
Ahmad Reza's avatar
Ahmad Reza committed
729
730
731
732
733
734
735
736
737
738
            return False

    def delete_particle(self):
        """
        Deletes a tile on current position

        :return: True: Deleting successful; False: Deleting unsuccessful
        """
        logging.info("Particle %s is", self.get_id())
        logging.info("is going to delete a particle on current position")
739
740
        if self.coordinates in self.world.get_particle_map_coordinates():
            if self.world.remove_particle_on(self.coordinates):
Ahmad Reza's avatar
Ahmad Reza committed
741
742
743
744
745
746
                self.csv_particle_writer.write_particle(particle_deleted=1)
                return True
        else:
            logging.info("Could not delet particle")
            return False

Karol Actun's avatar
Karol Actun committed
747
    def delete_particle_with(self, particle_id):
Ahmad Reza's avatar
Ahmad Reza committed
748
749
750
        """
        Deletes a particle with a given id

Karol Actun's avatar
Karol Actun committed
751
        :param particle_id: The id of the particle that should be deleted
Ahmad Reza's avatar
Ahmad Reza committed
752
753
754
        :return: True: Deleting successful; False: Deleting unsuccessful
        """
        logging.info("Particle %s is", self.get_id())
Karol Actun's avatar
Karol Actun committed
755
756
        logging.info("is going to delete a particle with id %s" % str(particle_id))
        if self.world.remove_particle(particle_id):
Ahmad Reza's avatar
Ahmad Reza committed
757
            self.csv_particle_writer.write_particle(particle_deleted=1)
758
            return True
Ahmad Reza's avatar
Ahmad Reza committed
759
        else:
Karol Actun's avatar
Karol Actun committed
760
            logging.info("Could not delet particle with particle id %s" % str(particle_id))
761
            return False
Ahmad Reza's avatar
Ahmad Reza committed
762

763
    def delete_particle_in(self, direction=None):
Ahmad Reza's avatar
Ahmad Reza committed
764
        """
765
        Deletes a particle either in a given directionection
Ahmad Reza's avatar
Ahmad Reza committed
766

767
        :param direction: The directionection on which the particle should be deleted. Options: E, SE, SW, W, NW, NE,
Ahmad Reza's avatar
Ahmad Reza committed
768
769
        :return: True: Deleting successful; False: Deleting unsuccessful
        """
770
        if direction is not None:
771
            coordinates = get_coordinates_in_direction(self.coordinates, direction)
Karol Actun's avatar
Karol Actun committed
772
            logging.info("Deleting tile in %s directionection" % str(direction))
773
            if self.world.remove_particle_on(coordinates):
Karol Actun's avatar
Karol Actun committed
774
                logging.info("Deleted particle with particle on coordinates %s" % str(coordinates))
Ahmad Reza's avatar
Ahmad Reza committed
775
                self.csv_particle_writer.write_particle(particle_deleted=1)
776
                return True
Ahmad Reza's avatar
Ahmad Reza committed
777
            else:
Karol Actun's avatar
Karol Actun committed
778
                logging.info("Could not delet particle on coordinates %s" % str(coordinates))
779
                return False
Ahmad Reza's avatar
Ahmad Reza committed
780

Karol Actun's avatar
Karol Actun committed
781
    def delete_particle_on(self, coordinates=None):
Ahmad Reza's avatar
Ahmad Reza committed
782
783
784
        """
        Deletes a particle either on a given x,y coordinates

Karol Actun's avatar
Karol Actun committed
785
        :param coordinates
Ahmad Reza's avatar
Ahmad Reza committed
786
787
        :return: True: Deleting successful; False: Deleting unsuccessful
        """
Karol Actun's avatar
Karol Actun committed
788
        if coordinates is not None:
Karol Actun's avatar
Karol Actun committed
789
            if self.world.grid.is_valid_location(coordinates):
790
                if self.world.remove_particle_on(coordinates):
Karol Actun's avatar
Karol Actun committed
791
                    logging.info("Deleted particle with particle on coordinates %s" % str(coordinates))
Ahmad Reza's avatar
Ahmad Reza committed
792
793
794
                    self.csv_particle_writer.write_particle(particle_deleted=1)
                    return True
                else:
Karol Actun's avatar
Karol Actun committed
795
                    logging.info("Could not delet particle on coordinates %s" % str(coordinates))
Ahmad Reza's avatar
Ahmad Reza committed
796
797
798
799
800
801
                    return False
            else:
                return False
        else:
            return False

Karol Actun's avatar
Karol Actun committed
802
    def take_particle_with(self, particle_id):
Ahmad Reza's avatar
Ahmad Reza committed
803
        """
Karol Actun's avatar
Karol Actun committed
804
        Takes a particle with a given tile id
Ahmad Reza's avatar
Ahmad Reza committed
805

Karol Actun's avatar
Karol Actun committed
806
        :param particle_id:  The id of the particle that should be taken
Ahmad Reza's avatar
Ahmad Reza committed
807
808
        :return: True: successful taken; False: unsuccessful taken
        """
Karol Actun's avatar
Karol Actun committed
809
810
811
812
813
814
815
816
817
        if self.carried_tile is None and self.carried_particle is None:
            if particle_id in self.world.get_particle_map_id():
                logging.info("particle with particle id %s is in the world" % str(particle_id))
                self.carried_particle = self.world.particle_map_id[particle_id]
                if self.carried_particle.take_me(self.coordinates):
                    logging.info("particle with particle id %s  has been taken" % str(particle_id))
                    self.carried_particle.coordinates = self.coordinates
                    self.world.vis.particle_changed(self.carried_particle)
                    self.world.csv_round.update_metrics(particles_taken=1)
Ahmad Reza's avatar
Ahmad Reza committed
818
819
820
                    self.csv_particle_writer.write_particle(particles_taken=1)
                    return True
                else:
Karol Actun's avatar
Karol Actun committed
821
                    logging.info("particle with particle id %s could not be taken" % str(particle_id))
Ahmad Reza's avatar
Ahmad Reza committed
822
823
                    return False
            else:
Karol Actun's avatar
Karol Actun committed
824
                logging.info("particle with particle id %s is not in the world" % str(particle_id))
Ahmad Reza's avatar
Ahmad Reza committed
825
        else:
Karol Actun's avatar
Karol Actun committed
826
            logging.info("particle cannot taken because particle is carrieng either a particle or a tile")
Ahmad Reza's avatar
Ahmad Reza committed
827

Karol Actun's avatar
Karol Actun committed
828
    def take_particle_on(self, coordinates):
Ahmad Reza's avatar
Ahmad Reza committed
829
        """
Karol Actun's avatar
Karol Actun committed
830
        Takes the particle on the given coordinates if it is not taken