aboutsummaryrefslogtreecommitdiff
path: root/tests
diff options
context:
space:
mode:
Diffstat (limited to 'tests')
-rw-r--r--tests/tween-test.scm136
1 files changed, 136 insertions, 0 deletions
diff --git a/tests/tween-test.scm b/tests/tween-test.scm
index ebe62e0..4420c94 100644
--- a/tests/tween-test.scm
+++ b/tests/tween-test.scm
@@ -79,4 +79,140 @@
(test-assert (tween-finished? tw3))
(test-equal "x stays" 20.0 (entity-ref e3 #:x)))))))
+(test-group "repeat"
+ (test-group "repeat: 1 plays twice"
+ (let* ((ent (list #:type 'a #:x 0))
+ (tw (make-tween ent props: '((#:x . 100)) duration: 100
+ ease: 'linear repeat: 1)))
+ (receive (tw2 e2) (tween-step tw ent 100)
+ (test-assert "not finished after first play" (not (tween-finished? tw2)))
+ (test-equal "x at target" 100.0 (entity-ref e2 #:x))
+ (receive (tw3 e3) (tween-step tw2 e2 100)
+ (test-assert "finished after second play" (tween-finished? tw3))
+ (test-equal "x at target again" 100.0 (entity-ref e3 #:x))))))
+
+ (test-group "repeat: -1 never finishes"
+ (let* ((ent (list #:type 'a #:x 0))
+ (tw (make-tween ent props: '((#:x . 10)) duration: 10
+ ease: 'linear repeat: -1)))
+ (let loop ((tw tw) (ent ent) (i 0))
+ (if (>= i 5) (test-assert "still active after 5 cycles" (tween-active? tw))
+ (receive (tw2 e2) (tween-step tw ent 10)
+ (test-assert "not finished" (not (tween-finished? tw2)))
+ (loop tw2 e2 (+ i 1)))))))
+
+ (test-group "repeat: 0 is default (no repeat)"
+ (let* ((ent (list #:type 'a #:x 0))
+ (tw (make-tween ent props: '((#:x . 50)) duration: 50 ease: 'linear)))
+ (receive (tw2 _e2) (tween-step tw ent 50)
+ (test-assert "finished immediately" (tween-finished? tw2)))))
+
+ (test-group "on-complete fires after last repeat"
+ (let ((calls 0))
+ (let* ((ent (list #:type 'a #:x 0))
+ (tw (make-tween ent props: '((#:x . 10)) duration: 10
+ ease: 'linear repeat: 1
+ on-complete: (lambda (_) (set! calls (+ calls 1))))))
+ (receive (tw2 e2) (tween-step tw ent 10)
+ (test-equal "no call after first play" 0 calls)
+ (receive (tw3 e3) (tween-step tw2 e2 10)
+ (test-equal "one call after last repeat" 1 calls))))))
+
+ (test-group "on-complete does not fire with repeat: -1"
+ (let ((calls 0))
+ (let* ((ent (list #:type 'a #:x 0))
+ (tw (make-tween ent props: '((#:x . 10)) duration: 10
+ ease: 'linear repeat: -1
+ on-complete: (lambda (_) (set! calls (+ calls 1))))))
+ (let loop ((tw tw) (ent ent) (i 0))
+ (if (>= i 5) (test-equal "never called" 0 calls)
+ (receive (tw2 e2) (tween-step tw ent 10)
+ (loop tw2 e2 (+ i 1)))))))))
+
+(test-group "yoyo"
+ (test-group "yoyo: #t with repeat: 1 reverses"
+ (let* ((ent (list #:type 'a #:x 0))
+ (tw (make-tween ent props: '((#:x . 100)) duration: 100
+ ease: 'linear repeat: 1 yoyo?: #t)))
+ (receive (tw2 e2) (tween-step tw ent 100)
+ (test-equal "x at target after forward" 100.0 (entity-ref e2 #:x))
+ (receive (tw3 e3) (tween-step tw2 e2 50)
+ (test-equal "x halfway back" 50.0 (entity-ref e3 #:x))
+ (receive (tw4 e4) (tween-step tw3 e3 50)
+ (test-assert "finished after reverse" (tween-finished? tw4))
+ (test-equal "x back to start" 0.0 (entity-ref e4 #:x)))))))
+
+ (test-group "yoyo: #t with repeat: -1 ping-pongs forever"
+ (let* ((ent (list #:type 'a #:x 0))
+ (tw (make-tween ent props: '((#:x . 100)) duration: 100
+ ease: 'linear repeat: -1 yoyo?: #t)))
+ ;; Forward
+ (receive (tw2 e2) (tween-step tw ent 100)
+ (test-equal "at target" 100.0 (entity-ref e2 #:x))
+ ;; Reverse
+ (receive (tw3 e3) (tween-step tw2 e2 100)
+ (test-equal "back to start" 0.0 (entity-ref e3 #:x))
+ ;; Forward again
+ (receive (tw4 e4) (tween-step tw3 e3 100)
+ (test-equal "at target again" 100.0 (entity-ref e4 #:x))
+ (test-assert "still active" (tween-active? tw4)))))))
+
+ (test-group "yoyo: #f with repeat: 1 replays same direction"
+ (let* ((ent (list #:type 'a #:x 0))
+ (tw (make-tween ent props: '((#:x . 100)) duration: 100
+ ease: 'linear repeat: 1 yoyo?: #f)))
+ (receive (tw2 e2) (tween-step tw ent 100)
+ (test-equal "x at target" 100.0 (entity-ref e2 #:x))
+ ;; Second play starts from same starts (0→100), but entity is at 100
+ ;; The tween replays 0→100 using original start values
+ (receive (tw3 e3) (tween-step tw2 e2 50)
+ (test-assert "not finished mid-repeat" (not (tween-finished? tw3)))))))
+
+ (test-group "yoyo: #t without repeat has no effect"
+ (let* ((ent (list #:type 'a #:x 0))
+ (tw (make-tween ent props: '((#:x . 100)) duration: 100
+ ease: 'linear repeat: 0 yoyo?: #t)))
+ (receive (tw2 e2) (tween-step tw ent 100)
+ (test-assert "finishes normally" (tween-finished? tw2))
+ (test-equal "x at target" 100.0 (entity-ref e2 #:x))))))
+
+(test-group "step-tweens pipeline"
+ (test-group "advances #:tween on entity"
+ (let* ((ent (list #:type 'a #:x 0
+ #:tween (make-tween (list #:x 0) props: '((#:x . 100))
+ duration: 100 ease: 'linear)))
+ (e2 (step-tweens ent 50)))
+ (test-equal "x moved to midpoint" 50.0 (entity-ref e2 #:x))
+ (test-assert "tween still attached" (entity-ref e2 #:tween #f))))
+
+ (test-group "removes #:tween when finished"
+ (let* ((ent (list #:type 'a #:x 0
+ #:tween (make-tween (list #:x 0) props: '((#:x . 100))
+ duration: 100 ease: 'linear)))
+ (e2 (step-tweens ent 100)))
+ (test-equal "x at target" 100.0 (entity-ref e2 #:x))
+ (test-equal "tween removed" #f (entity-ref e2 #:tween #f))))
+
+ (test-group "no-op without #:tween"
+ (let* ((ent (list #:type 'a #:x 42))
+ (e2 (step-tweens ent 100)))
+ (test-equal "x unchanged" 42 (entity-ref e2 #:x))))
+
+ (test-group "keeps repeating tween attached"
+ (let* ((ent (list #:type 'a #:x 0
+ #:tween (make-tween (list #:x 0) props: '((#:x . 100))
+ duration: 100 ease: 'linear repeat: -1 yoyo?: #t)))
+ (e2 (step-tweens ent 100)))
+ (test-equal "x at target" 100.0 (entity-ref e2 #:x))
+ (test-assert "tween still attached (repeating)" (entity-ref e2 #:tween #f))))
+
+ (test-group "respects #:skip-pipelines"
+ (let* ((ent (list #:type 'a #:x 0
+ #:skip-pipelines '(tweens)
+ #:tween (make-tween (list #:x 0) props: '((#:x . 100))
+ duration: 100 ease: 'linear)))
+ (e2 (step-tweens ent 100)))
+ (test-equal "x unchanged (skipped)" 0 (entity-ref e2 #:x))
+ (test-assert "tween still there" (entity-ref e2 #:tween #f)))))
+
(test-end "tween")