Kaynağa Gözat

Move with rotation: sometimes, rotation skiped. Closes #43

Bastien Sevajol 6 yıl önce
ebeveyn
işleme
2b9cc16141
2 değiştirilmiş dosya ile 87 ekleme ve 3 silme
  1. 7 3
      opencombat/simulation/move.py
  2. 80 0
      tests/move/test_move.py

+ 7 - 3
opencombat/simulation/move.py Dosyayı Görüntüle

@@ -267,11 +267,13 @@ class MoveWithRotationBehaviour(SubjectBehaviour):
267 267
                 # look at progression
268 268
                 rotate_since = now - self.subject.start_rotation
269 269
                 rotate_progress = rotate_since / self.subject.rotate_duration
270
-                rotation_to_do = self.subject.rotate_to - self.subject.direction
270
+                rotation_to_do = self.subject.rotate_to - self.subject.direction  # nopep8
271 271
                 rotation_done = rotation_to_do * rotate_progress
272 272
                 self.subject.direction = self.subject.direction + rotation_done
273 273
                 rotation_left = self.subject.rotate_to - self.subject.direction
274
-                duration = self.subject.get_rotate_duration(angle=rotation_left)
274
+                duration = abs(self.subject.get_rotate_duration(
275
+                    angle=rotation_left,
276
+                ))
275 277
                 self.subject.rotate_duration = duration
276 278
                 self.subject.start_rotation = now
277 279
 
@@ -282,7 +284,9 @@ class MoveWithRotationBehaviour(SubjectBehaviour):
282 284
                     gui_action=data['gui_action'],
283 285
                 )]
284 286
             else:
285
-                duration = self.subject.get_rotate_duration(angle=data['rotate_relative'])
287
+                duration = abs(self.subject.get_rotate_duration(
288
+                    angle=data['rotate_relative'],
289
+                ))
286 290
                 self.subject.rotate_to = data['rotate_absolute']
287 291
                 self.subject.rotate_duration = duration
288 292
                 self.subject.start_rotation = time.time()

+ 80 - 0
tests/move/test_move.py Dosyayı Görüntüle

@@ -507,3 +507,83 @@ def test_move_behaviour(config):
507 507
         assert -1 == subject.move_duration
508 508
         with pytest.raises(KeyError):
509 509
             assert subject.intentions.get(MoveToIntention)
510
+
511
+def test_move_and_rotate_behaviour__rotate_negatively(config):
512
+    simulation = XYZSimulation(config)
513
+    simulation.physics.graph.add_edge('0.0', '1.-1', {})
514
+    simulation.physics.graph.add_edge('1.-1', '2.-1', {})
515
+
516
+    subject = TankSubject(
517
+        config,
518
+        simulation,
519
+        position=(0, 0),
520
+    )
521
+    move = MoveToIntention(
522
+        to=(2, -1),
523
+        gui_action=UserAction.ORDER_MOVE,
524
+    )
525
+    subject.intentions.set(move)
526
+
527
+    move_behaviour = MoveWithRotationBehaviour(
528
+        config=config,
529
+        simulation=simulation,
530
+        subject=subject,
531
+    )
532
+
533
+    # First is a move
534
+    with freeze_time("2000-01-01 00:00:00", tz_offset=0):
535
+        data = move_behaviour.run({MoveToMechanism: move.get_data()})
536
+        assert {
537
+                   'gui_action': UserAction.ORDER_MOVE,
538
+                   'path': [
539
+                       (0, 0),
540
+                       (1, -1),
541
+                       (2, -1),
542
+                   ],
543
+                   'rotate_absolute': 135.0,
544
+                   'rotate_relative': 135.0,
545
+               } == data
546
+
547
+        events = move_behaviour.action(data)
548
+        assert 1 == len(events)
549
+        assert isinstance(events[0], SubjectStartRotationEvent)
550
+        assert 135 == events[0].rotate_relative
551
+        assert 135 == events[0].rotate_absolute
552
+        assert 15 == round(events[0].duration)
553
+        assert subject.intentions.get(MoveToIntention)
554
+
555
+    with freeze_time("2000-01-01 00:00:15", tz_offset=0):
556
+        data = move_behaviour.run({MoveToMechanism: move.get_data()})
557
+        assert {
558
+                   'gui_action': UserAction.ORDER_MOVE,
559
+                   'rotate_to_finished': 135,
560
+                   'tile_move_to': (1, -1),
561
+               } == data
562
+
563
+        events = move_behaviour.action(data)
564
+        assert 2 == len(events)
565
+        assert isinstance(events[1], SubjectStartTileMoveEvent)
566
+        assert isinstance(events[0], SubjectFinishRotationEvent)
567
+        assert (1, -1) == events[1].move_to
568
+        assert 9.0 == events[1].duration
569
+        assert 135 == events[0].rotation_absolute
570
+        assert subject.intentions.get(MoveToIntention)
571
+
572
+    with freeze_time("2000-01-01 00:00:24", tz_offset=0):
573
+        data = move_behaviour.run({MoveToMechanism: move.get_data()})
574
+        assert {
575
+                   'gui_action': UserAction.ORDER_MOVE,
576
+                   'rotate_absolute': 90,
577
+                   'rotate_relative': -45,
578
+                   'tile_move_to_finished': (1, -1),
579
+               } == data
580
+
581
+        events = move_behaviour.action(data)
582
+        assert 2 == len(events)
583
+        assert isinstance(events[0], SubjectFinishTileMoveEvent)
584
+        assert isinstance(events[1], SubjectStartRotationEvent)
585
+        assert (1, -1) == events[0].move_to
586
+        assert 90 == events[1].rotate_absolute
587
+        assert -45 == events[1].rotate_relative
588
+        assert 5 == round(events[1].duration)
589
+        assert subject.intentions.get(MoveToIntention)