@@ -628,66 +628,54 @@ def _impl_test_interactive_timers():
628628 import matplotlib .pyplot as plt
629629
630630 fig = plt .figure ()
631- event_loop_time = 0.5 # in seconds
631+ event_loop_time = 1 # in seconds
632+ expected_200ms_calls = int (event_loop_time / 0.2 )
632633
633- # A timer with <1 millisecond gets converted to int and therefore 0
634- # milliseconds, which the mac framework interprets as singleshot.
635- # We only want singleshot if we specify that ourselves, otherwise we want
636- # a repeating timer
637- timer_repeating = fig .canvas .new_timer (0.1 )
634+ # Start at 2s interval (would only get one firing), then update to 200ms
635+ timer_repeating = fig .canvas .new_timer (2000 )
638636 mock_repeating = Mock ()
639637 timer_repeating .add_callback (mock_repeating )
640638
641639 timer_single_shot = fig .canvas .new_timer (100 )
642640 mock_single_shot = Mock ()
643641 timer_single_shot .add_callback (mock_single_shot )
644642
645- # 100ms timer triggers and the callback takes 75ms to run
646- # Test that we don't drift and that we get called on every 100ms
647- # interval and not every 175ms
648- mock_slow_callback = Mock ()
649- mock_slow_callback .side_effect = lambda : time .sleep (0.075 )
650- timer_slow_callback = fig .canvas .new_timer (100 )
651- timer_slow_callback .add_callback (mock_slow_callback )
652-
653643 timer_repeating .start ()
644+ # Test updating the interval updates a running timer
645+ timer_repeating .interval = 200
654646 # Start as a repeating timer then change to singleshot via the attribute
655647 timer_single_shot .start ()
656648 timer_single_shot .single_shot = True
657- timer_slow_callback . start ()
649+
658650 fig .canvas .start_event_loop (event_loop_time )
659- # NOTE: The timer is as fast as possible, but this is different between backends
660- # so we can't assert on the exact number but it should be faster than 100ms
661- expected_100ms_calls = int (event_loop_time / 0.1 )
662- assert mock_repeating .call_count > expected_100ms_calls , \
663- f"Expected more than { expected_100ms_calls } calls, " \
651+ assert 1 < mock_repeating .call_count <= expected_200ms_calls + 1 , \
652+ f"Interval update: Expected between 2 and { expected_200ms_calls + 1 } calls, " \
664653 f"got { mock_repeating .call_count } "
665654 assert mock_single_shot .call_count == 1 , \
666- f"Expected 1 call, got { mock_single_shot .call_count } "
667- assert mock_slow_callback .call_count >= expected_100ms_calls - 1 , \
668- f"Expected at least { expected_100ms_calls - 1 } calls, " \
669- f"got { mock_slow_callback .call_count } "
655+ f"Singleshot: Expected 1 call, got { mock_single_shot .call_count } "
670656
671- # Test updating the interval updates a running timer
672- timer_repeating .interval = 100
657+ # 200ms timer triggers and the callback takes 100ms to run
658+ # Test that we don't drift and that we get called on every 200ms
659+ # interval and not every 300ms
660+ mock_repeating .side_effect = lambda : time .sleep (0.1 )
673661 mock_repeating .call_count = 0
674662 # Make sure we can start the timer after stopping a singleshot timer
675663 timer_single_shot .stop ()
676664 timer_single_shot .start ()
677665
678666 fig .canvas .start_event_loop (event_loop_time )
679- assert 1 < mock_repeating .call_count <= expected_100ms_calls + 1 , \
680- f"Expected less than { expected_100ms_calls + 1 } calls, " \
681- "got {mock.call_count}"
667+ # Not exact timers, so add a little slop. We really want to make sure we are
668+ # getting more than 3 (every 300ms).
669+ assert mock_repeating .call_count >= expected_200ms_calls - 1 , \
670+ f"Slow callback: Expected at least { expected_200ms_calls - 1 } calls, " \
671+ f"got { mock_repeating .call_count } "
682672 assert mock_single_shot .call_count == 2 , \
683- f"Expected 2 calls, got { mock_single_shot .call_count } "
673+ f"Singleshot: Expected 2 calls, got { mock_single_shot .call_count } "
684674 plt .close ("all" )
685675
686676
687677@pytest .mark .parametrize ("env" , _get_testable_interactive_backends ())
688678def test_interactive_timers (env ):
689- if env ["MPLBACKEND" ] == "gtk3cairo" and os .getenv ("CI" ):
690- pytest .skip ("gtk3cairo timers do not work in remote CI" )
691679 if env ["MPLBACKEND" ] == "wx" :
692680 pytest .skip ("wx backend is deprecated; tests failed on appveyor" )
693681 _run_helper (_impl_test_interactive_timers ,
0 commit comments