1use std::f32::consts::TAU;
10use glam::{Vec3, Vec4};
11
12use super::easing::Easing;
13use super::tween_manager::{TweenManager, TweenTarget, TweenId, BarId};
14use crate::glyph::GlyphId;
15
16pub fn menu_cursor_slide(
22 mgr: &mut TweenManager,
23 cursor_glyph: GlyphId,
24 from_y: f32,
25 to_y: f32,
26) -> TweenId {
27 mgr.cancel_glyph(cursor_glyph);
28 mgr.start(
29 TweenTarget::GlyphPositionY(cursor_glyph),
30 from_y, to_y, 0.1,
31 Easing::EaseOutCubic,
32 )
33}
34
35pub fn menu_cursor_pulse(
37 mgr: &mut TweenManager,
38 cursor_glyph: GlyphId,
39) -> TweenId {
40 mgr.start(
41 TweenTarget::GlyphEmission(cursor_glyph),
42 0.3, 0.8, 0.6,
43 Easing::EaseInOutSine,
44 )
45}
46
47pub fn menu_select_flash(
49 mgr: &mut TweenManager,
50 glyphs: &[GlyphId],
51) -> Vec<TweenId> {
52 let mut ids = Vec::new();
53 for &glyph in glyphs {
54 ids.push(mgr.start(
55 TweenTarget::GlyphEmission(glyph),
56 0.0, 2.0, 0.08,
57 Easing::EaseOutExpo,
58 ));
59 ids.push(mgr.start_delayed(
60 TweenTarget::GlyphEmission(glyph),
61 2.0, 0.0, 0.2, 0.08,
62 Easing::EaseInQuad,
63 ));
64 }
65 ids
66}
67
68pub fn screen_crossfade(
70 mgr: &mut TweenManager,
71 fade_duration: f32,
72 on_midpoint: impl FnOnce(&mut TweenManager) + Send + 'static,
73) -> TweenId {
74 mgr.start_with_callback(
75 TweenTarget::ScreenFade,
76 0.0, 1.0, fade_duration,
77 Easing::EaseInQuad,
78 move |mgr| {
79 on_midpoint(mgr);
80 mgr.start(
81 TweenTarget::ScreenFade,
82 1.0, 0.0, fade_duration,
83 Easing::EaseOutQuad,
84 );
85 },
86 )
87}
88
89pub fn screen_fade_through_black(
91 mgr: &mut TweenManager,
92 fade_out: f32,
93 hold: f32,
94 fade_in: f32,
95) -> TweenId {
96 mgr.start_with_callback(
97 TweenTarget::ScreenFade,
98 0.0, 1.0, fade_out,
99 Easing::EaseInQuad,
100 move |mgr| {
101 mgr.start_delayed(
102 TweenTarget::ScreenFade,
103 1.0, 0.0, fade_in, hold,
104 Easing::EaseOutQuad,
105 );
106 },
107 )
108}
109
110pub fn hp_bar_change(
116 mgr: &mut TweenManager,
117 bar: BarId,
118 from_pct: f32,
119 to_pct: f32,
120) -> TweenId {
121 mgr.start_tagged(
122 TweenTarget::BarFillPercent(bar),
123 from_pct, to_pct, 0.3,
124 Easing::EaseOutQuad,
125 "hp_bar",
126 )
127}
128
129pub fn hp_ghost_bar(
131 mgr: &mut TweenManager,
132 bar: BarId,
133 from_pct: f32,
134 to_pct: f32,
135) -> TweenId {
136 mgr.start_delayed(
137 TweenTarget::BarGhostPercent(bar),
138 from_pct, to_pct, 0.5, 0.3,
139 Easing::EaseInQuad,
140 )
141}
142
143pub fn hp_bar_damage(
145 mgr: &mut TweenManager,
146 bar: BarId,
147 old_pct: f32,
148 new_pct: f32,
149) -> (TweenId, TweenId) {
150 let fill = hp_bar_change(mgr, bar, old_pct, new_pct);
151 let ghost = hp_ghost_bar(mgr, bar, old_pct, new_pct);
152 (fill, ghost)
153}
154
155pub fn mp_bar_change(
157 mgr: &mut TweenManager,
158 bar: BarId,
159 from_pct: f32,
160 to_pct: f32,
161) -> TweenId {
162 mgr.start_tagged(
163 TweenTarget::BarFillPercent(bar),
164 from_pct, to_pct, 0.25,
165 Easing::EaseOutCubic,
166 "mp_bar",
167 )
168}
169
170pub fn xp_bar_fill(
172 mgr: &mut TweenManager,
173 bar: BarId,
174 from_pct: f32,
175 to_pct: f32,
176) -> TweenId {
177 mgr.start(
178 TweenTarget::BarFillPercent(bar),
179 from_pct, to_pct, 0.8,
180 Easing::EaseOutBack,
181 )
182}
183
184pub fn damage_number_arc(
190 mgr: &mut TweenManager,
191 glyph: GlyphId,
192 start_y: f32,
193 rise_height: f32,
194) -> Vec<TweenId> {
195 vec![
196 mgr.start(
198 TweenTarget::GlyphPositionY(glyph),
199 start_y, start_y + rise_height, 1.0,
200 Easing::EaseOutQuad,
201 ),
202 mgr.start(
204 TweenTarget::GlyphAlpha(glyph),
205 1.0, 0.0, 1.0,
206 Easing::EaseInQuad,
207 ),
208 mgr.start(
210 TweenTarget::GlyphScale(glyph),
211 2.0, 1.0, 0.2,
212 Easing::Spring { stiffness: 8.0, damping: 0.4 },
213 ),
214 ]
215}
216
217pub fn crit_damage_number(
219 mgr: &mut TweenManager,
220 glyph: GlyphId,
221 start_y: f32,
222 rise_height: f32,
223) -> Vec<TweenId> {
224 vec![
225 mgr.start(
226 TweenTarget::GlyphPositionY(glyph),
227 start_y, start_y + rise_height * 1.5, 1.2,
228 Easing::EaseOutQuad,
229 ),
230 mgr.start(
231 TweenTarget::GlyphAlpha(glyph),
232 1.0, 0.0, 1.2,
233 Easing::EaseInCubic,
234 ),
235 mgr.start(
236 TweenTarget::GlyphScale(glyph),
237 3.0, 1.2, 0.3,
238 Easing::Spring { stiffness: 6.0, damping: 0.3 },
239 ),
240 mgr.start(
242 TweenTarget::GlyphEmission(glyph),
243 3.0, 0.5, 0.3,
244 Easing::EaseOutExpo,
245 ),
246 ]
247}
248
249pub fn heal_number(
251 mgr: &mut TweenManager,
252 glyph: GlyphId,
253 start_y: f32,
254) -> Vec<TweenId> {
255 vec![
256 mgr.start(
257 TweenTarget::GlyphPositionY(glyph),
258 start_y, start_y + 2.0, 0.8,
259 Easing::EaseOutSine,
260 ),
261 mgr.start(
262 TweenTarget::GlyphAlpha(glyph),
263 1.0, 0.0, 0.8,
264 Easing::EaseInQuad,
265 ),
266 mgr.start(
267 TweenTarget::GlyphScale(glyph),
268 1.5, 1.0, 0.15,
269 Easing::EaseOutBack,
270 ),
271 ]
272}
273
274pub fn stat_increase_flash(
280 mgr: &mut TweenManager,
281 glyph: GlyphId,
282) -> Vec<TweenId> {
283 vec![
284 mgr.start(
286 TweenTarget::GlyphEmission(glyph),
287 0.0, 2.0, 0.1,
288 Easing::EaseOutQuad,
289 ),
290 mgr.start_delayed(
292 TweenTarget::GlyphEmission(glyph),
293 2.0, 0.0, 0.3, 0.1,
294 Easing::EaseInQuad,
295 ),
296 mgr.start(
298 TweenTarget::GlyphScale(glyph),
299 1.0, 1.3, 0.08,
300 Easing::EaseOutQuad,
301 ),
302 mgr.start_delayed(
303 TweenTarget::GlyphScale(glyph),
304 1.3, 1.0, 0.15, 0.08,
305 Easing::EaseOutBack,
306 ),
307 ]
308}
309
310pub fn stat_decrease_flash(
312 mgr: &mut TweenManager,
313 glyph: GlyphId,
314) -> Vec<TweenId> {
315 vec![
316 mgr.start(
317 TweenTarget::GlyphColorR(glyph),
318 1.0, 1.0, 0.1,
319 Easing::Flash,
320 ),
321 mgr.start(
322 TweenTarget::GlyphEmission(glyph),
323 0.0, 1.5, 0.08,
324 Easing::EaseOutQuad,
325 ),
326 mgr.start_delayed(
327 TweenTarget::GlyphEmission(glyph),
328 1.5, 0.0, 0.2, 0.08,
329 Easing::EaseInQuad,
330 ),
331 ]
332}
333
334pub fn status_effect_apply(
340 mgr: &mut TweenManager,
341 entity_glyphs: &[GlyphId],
342 emission_color_intensity: f32,
343) -> Vec<TweenId> {
344 let mut ids = Vec::new();
345 for &glyph in entity_glyphs {
346 ids.push(mgr.start(
347 TweenTarget::GlyphEmission(glyph),
348 0.0, emission_color_intensity, 0.15,
349 Easing::EaseOutExpo,
350 ));
351 ids.push(mgr.start_delayed(
352 TweenTarget::GlyphEmission(glyph),
353 emission_color_intensity, 0.0, 0.3, 0.15,
354 Easing::EaseInQuad,
355 ));
356 }
357 ids
358}
359
360pub fn level_up_ring(
369 mgr: &mut TweenManager,
370 ring_glyphs: &[GlyphId],
371 center_x: f32,
372 center_y: f32,
373 max_radius: f32,
374) -> Vec<TweenId> {
375 let count = ring_glyphs.len();
376 let mut ids = Vec::new();
377
378 for (i, &glyph) in ring_glyphs.iter().enumerate() {
379 let angle = i as f32 * TAU / count as f32;
380 let target_x = center_x + angle.cos() * max_radius;
381 let target_y = center_y + angle.sin() * max_radius;
382
383 ids.push(mgr.start(
385 TweenTarget::GlyphPositionX(glyph),
386 center_x, target_x, 0.5,
387 Easing::EaseOutQuad,
388 ));
389 ids.push(mgr.start(
390 TweenTarget::GlyphPositionY(glyph),
391 center_y, target_y, 0.5,
392 Easing::EaseOutQuad,
393 ));
394 ids.push(mgr.start(
396 TweenTarget::GlyphAlpha(glyph),
397 1.0, 0.0, 0.5,
398 Easing::EaseInQuad,
399 ));
400 ids.push(mgr.start(
402 TweenTarget::GlyphEmission(glyph),
403 2.0, 0.0, 0.5,
404 Easing::EaseOutQuad,
405 ));
406 }
407
408 ids
409}
410
411pub fn level_up_screen_flash(mgr: &mut TweenManager) -> Vec<TweenId> {
413 vec![
414 mgr.start(TweenTarget::ScreenBloom, 0.5, 2.0, 0.15, Easing::EaseOutExpo),
415 mgr.start_delayed(TweenTarget::ScreenBloom, 2.0, 0.5, 0.4, 0.15, Easing::EaseInQuad),
416 mgr.start(TweenTarget::ScreenVignette, 0.0, 0.4, 0.1, Easing::EaseOutQuad),
417 mgr.start_delayed(TweenTarget::ScreenVignette, 0.4, 0.0, 0.3, 0.1, Easing::EaseInQuad),
418 ]
419}
420
421pub fn entity_hit_recoil(
427 mgr: &mut TweenManager,
428 entity_glyphs: &[GlyphId],
429 hit_direction_x: f32,
430) -> Vec<TweenId> {
431 let mut ids = Vec::new();
432 for &glyph in entity_glyphs {
433 ids.push(mgr.start(
435 TweenTarget::GlyphScaleX(glyph),
436 1.0, 0.8, 0.05,
437 Easing::EaseOutQuad,
438 ));
439 ids.push(mgr.start_delayed(
440 TweenTarget::GlyphScaleX(glyph),
441 0.8, 1.0, 0.1, 0.05,
442 Easing::EaseOutBack,
443 ));
444 ids.push(mgr.start(
445 TweenTarget::GlyphScaleY(glyph),
446 1.0, 1.2, 0.05,
447 Easing::EaseOutQuad,
448 ));
449 ids.push(mgr.start_delayed(
450 TweenTarget::GlyphScaleY(glyph),
451 1.2, 1.0, 0.1, 0.05,
452 Easing::EaseOutBack,
453 ));
454 ids.push(mgr.start(
456 TweenTarget::GlyphEmission(glyph),
457 0.0, 1.5, 0.05,
458 Easing::Flash,
459 ));
460 ids.push(mgr.start_delayed(
461 TweenTarget::GlyphEmission(glyph),
462 1.5, 0.0, 0.15, 0.05,
463 Easing::EaseInQuad,
464 ));
465 }
466 ids.push(mgr.start(TweenTarget::CameraTrauma, 0.0, 0.3, 0.1, Easing::Flash));
468 ids
469}
470
471pub fn boss_entrance(mgr: &mut TweenManager) -> Vec<TweenId> {
473 vec![
474 mgr.start(TweenTarget::ScreenVignette, 0.0, 0.8, 0.3, Easing::EaseInQuad),
476 mgr.start_delayed(TweenTarget::ScreenVignette, 0.8, 0.2, 0.5, 0.3, Easing::EaseOutQuad),
477 mgr.start(TweenTarget::ScreenChromaticAberration, 0.0, 0.8, 0.2, Easing::EaseOutExpo),
479 mgr.start_delayed(TweenTarget::ScreenChromaticAberration, 0.8, 0.0, 0.4, 0.2, Easing::EaseInQuad),
480 mgr.start(TweenTarget::ScreenSaturation, 1.0, 0.3, 0.3, Easing::EaseInQuad),
482 mgr.start_delayed(TweenTarget::ScreenSaturation, 0.3, 1.0, 0.5, 0.3, Easing::EaseOutQuad),
483 mgr.start(TweenTarget::CameraTrauma, 0.0, 0.5, 0.3, Easing::EaseOutExpo),
485 ]
486}
487
488pub fn combat_hit_shake(
490 mgr: &mut TweenManager,
491 intensity: f32,
492) -> TweenId {
493 mgr.start(
494 TweenTarget::CameraTrauma,
495 0.0, intensity, 0.08,
496 Easing::Flash,
497 )
498}
499
500pub fn death_text_reveal(
506 mgr: &mut TweenManager,
507 text_glyphs: &[GlyphId],
508) -> Vec<TweenId> {
509 let mut ids = Vec::new();
510 for (i, &glyph) in text_glyphs.iter().enumerate() {
511 let delay = i as f32 * 0.03; ids.push(mgr.start_delayed(
513 TweenTarget::GlyphScale(glyph),
514 0.0, 1.0, 0.4, delay,
515 Easing::Spring { stiffness: 6.0, damping: 0.35 },
516 ));
517 ids.push(mgr.start_delayed(
518 TweenTarget::GlyphAlpha(glyph),
519 0.0, 1.0, 0.2, delay,
520 Easing::EaseOutQuad,
521 ));
522 }
523 ids.push(mgr.start(TweenTarget::ScreenSaturation, 1.0, 0.0, 1.5, Easing::EaseInQuad));
525 ids.push(mgr.start(TweenTarget::ScreenVignette, 0.0, 0.9, 1.0, Easing::EaseInCubic));
526 ids.push(mgr.start(TweenTarget::ScreenChromaticAberration, 0.0, 0.3, 0.5, Easing::EaseOutQuad));
527 ids
528}
529
530pub fn entity_death_scatter(
532 mgr: &mut TweenManager,
533 entity_glyphs: &[GlyphId],
534 entity_x: f32,
535 entity_y: f32,
536) -> Vec<TweenId> {
537 let mut ids = Vec::new();
538 let count = entity_glyphs.len();
539 for (i, &glyph) in entity_glyphs.iter().enumerate() {
540 let angle = i as f32 * TAU / count.max(1) as f32;
541 let dist = 3.0 + (i as f32 * 0.5);
542 ids.push(mgr.start(
543 TweenTarget::GlyphPositionX(glyph),
544 entity_x, entity_x + angle.cos() * dist, 0.6,
545 Easing::EaseOutQuad,
546 ));
547 ids.push(mgr.start(
548 TweenTarget::GlyphPositionY(glyph),
549 entity_y, entity_y + angle.sin() * dist, 0.6,
550 Easing::EaseOutQuad,
551 ));
552 ids.push(mgr.start(
553 TweenTarget::GlyphAlpha(glyph),
554 1.0, 0.0, 0.6,
555 Easing::EaseInQuad,
556 ));
557 ids.push(mgr.start(
558 TweenTarget::GlyphRotation(glyph),
559 0.0, TAU * (if i % 2 == 0 { 1.0 } else { -1.0 }), 0.6,
560 Easing::EaseOutQuad,
561 ));
562 }
563 ids
564}
565
566pub fn score_roll_up(
572 mgr: &mut TweenManager,
573 final_score: f32,
574 duration: f32,
575) -> TweenId {
576 mgr.start(
577 TweenTarget::Named("score_display".to_string()),
578 0.0, final_score, duration,
579 Easing::EaseOutCubic,
580 )
581}
582
583pub fn victory_text_drop(
585 mgr: &mut TweenManager,
586 text_glyphs: &[GlyphId],
587 target_y: f32,
588) -> Vec<TweenId> {
589 let mut ids = Vec::new();
590 for (i, &glyph) in text_glyphs.iter().enumerate() {
591 let delay = i as f32 * 0.05;
592 ids.push(mgr.start_delayed(
593 TweenTarget::GlyphPositionY(glyph),
594 target_y + 10.0, target_y, 0.4, delay,
595 Easing::EaseOutBounce,
596 ));
597 ids.push(mgr.start_delayed(
598 TweenTarget::GlyphAlpha(glyph),
599 0.0, 1.0, 0.1, delay,
600 Easing::EaseOutQuad,
601 ));
602 ids.push(mgr.start_delayed(
603 TweenTarget::GlyphEmission(glyph),
604 2.0, 0.3, 0.3, delay,
605 Easing::EaseOutQuad,
606 ));
607 }
608 ids.push(mgr.start(TweenTarget::ScreenBloom, 0.5, 3.0, 0.2, Easing::EaseOutExpo));
610 ids.push(mgr.start_delayed(TweenTarget::ScreenBloom, 3.0, 0.5, 0.5, 0.2, Easing::EaseInQuad));
611 ids
612}
613
614pub fn entity_assemble(
620 mgr: &mut TweenManager,
621 glyph_starts: &[(GlyphId, f32, f32)], glyph_targets: &[(f32, f32)], stagger: f32,
624) -> Vec<TweenId> {
625 let mut ids = Vec::new();
626 for (i, ((glyph, sx, sy), (tx, ty))) in glyph_starts.iter().zip(glyph_targets.iter()).enumerate() {
627 let delay = i as f32 * stagger;
628 ids.push(mgr.start_delayed(
629 TweenTarget::GlyphPositionX(*glyph),
630 *sx, *tx, 0.3, delay,
631 Easing::EaseOutBack,
632 ));
633 ids.push(mgr.start_delayed(
634 TweenTarget::GlyphPositionY(*glyph),
635 *sy, *ty, 0.3, delay,
636 Easing::EaseOutBack,
637 ));
638 ids.push(mgr.start_delayed(
639 TweenTarget::GlyphAlpha(*glyph),
640 0.0, 1.0, 0.15, delay,
641 Easing::EaseOutQuad,
642 ));
643 }
644 ids
645}
646
647pub fn crafting_shatter(
653 mgr: &mut TweenManager,
654 glyphs: &[GlyphId],
655 center_x: f32,
656 center_y: f32,
657) -> Vec<TweenId> {
658 entity_death_scatter(mgr, glyphs, center_x, center_y)
659}
660
661pub fn crafting_forge(
663 mgr: &mut TweenManager,
664 glyph_positions: &[(GlyphId, f32, f32)],
665 center_x: f32,
666 center_y: f32,
667) -> Vec<TweenId> {
668 let mut ids = Vec::new();
669 for (i, (glyph, sx, sy)) in glyph_positions.iter().enumerate() {
670 let delay = i as f32 * 0.02;
671 ids.push(mgr.start_delayed(
672 TweenTarget::GlyphPositionX(*glyph),
673 *sx, center_x, 0.3, delay,
674 Easing::EaseInQuad,
675 ));
676 ids.push(mgr.start_delayed(
677 TweenTarget::GlyphPositionY(*glyph),
678 *sy, center_y, 0.3, delay,
679 Easing::EaseInQuad,
680 ));
681 }
682 ids.push(mgr.start_delayed(TweenTarget::ScreenBloom, 0.5, 3.0, 0.1, 0.3, Easing::Flash));
684 ids.push(mgr.start_delayed(TweenTarget::ScreenBloom, 3.0, 0.5, 0.3, 0.4, Easing::EaseInQuad));
685 ids.push(mgr.start_delayed(TweenTarget::CameraTrauma, 0.0, 0.2, 0.1, 0.3, Easing::Flash));
686 ids
687}
688
689pub fn room_cursor_slide(
695 mgr: &mut TweenManager,
696 cursor_glyph: GlyphId,
697 from_x: f32,
698 from_y: f32,
699 to_x: f32,
700 to_y: f32,
701) -> Vec<TweenId> {
702 mgr.cancel_glyph(cursor_glyph);
703 vec![
704 mgr.start(TweenTarget::GlyphPositionX(cursor_glyph), from_x, to_x, 0.15, Easing::EaseOutCubic),
705 mgr.start(TweenTarget::GlyphPositionY(cursor_glyph), from_y, to_y, 0.15, Easing::EaseOutCubic),
706 ]
707}
708
709pub fn room_transition_pan(
711 mgr: &mut TweenManager,
712 from_x: f32,
713 to_x: f32,
714 from_y: f32,
715 to_y: f32,
716) -> Vec<TweenId> {
717 mgr.cancel_tag("room_pan");
718 vec![
719 mgr.start_tagged(TweenTarget::CameraPositionX, from_x, to_x, 0.3, Easing::EaseInOutCubic, "room_pan"),
720 mgr.start_tagged(TweenTarget::CameraPositionY, from_y, to_y, 0.3, Easing::EaseInOutCubic, "room_pan"),
721 ]
722}
723
724pub fn pulse_emission(
731 mgr: &mut TweenManager,
732 glyph: GlyphId,
733 min_emission: f32,
734 max_emission: f32,
735 period: f32,
736) -> TweenId {
737 let tween = super::Tween::new(min_emission, max_emission, period * 0.5, Easing::EaseInOutSine)
739 .with_repeat(-1, true);
740 let state = super::TweenState::new(tween);
741 mgr.push_raw(
742 TweenTarget::GlyphEmission(glyph),
743 state,
744 0.0,
745 Some("pulse".to_string()),
746 None,
747 )
748}
749
750pub fn typewriter_reveal(
752 mgr: &mut TweenManager,
753 glyphs: &[GlyphId],
754 chars_per_second: f32,
755) -> Vec<TweenId> {
756 let mut ids = Vec::new();
757 let interval = 1.0 / chars_per_second.max(0.01);
758 for (i, &glyph) in glyphs.iter().enumerate() {
759 let delay = i as f32 * interval;
760 ids.push(mgr.start_delayed(
761 TweenTarget::GlyphAlpha(glyph),
762 0.0, 1.0, 0.05, delay,
763 Easing::Step,
764 ));
765 }
766 ids
767}
768
769#[cfg(test)]
772mod tests {
773 use super::*;
774
775 #[test]
776 fn damage_number_arc_creates_three_tweens() {
777 let mut mgr = TweenManager::new();
778 let glyph = GlyphId(42);
779 let ids = damage_number_arc(&mut mgr, glyph, 0.0, 3.0);
780 assert_eq!(ids.len(), 3);
781 }
782
783 #[test]
784 fn hp_bar_damage_creates_two_tweens() {
785 let mut mgr = TweenManager::new();
786 let bar = BarId(0);
787 let (fill, ghost) = hp_bar_damage(&mut mgr, bar, 1.0, 0.7);
788 assert!(mgr.is_active(fill));
789 assert!(mgr.is_active(ghost));
790 }
791
792 #[test]
793 fn level_up_ring_creates_four_per_glyph() {
794 let mut mgr = TweenManager::new();
795 let glyphs = vec![GlyphId(0), GlyphId(1), GlyphId(2)];
796 let ids = level_up_ring(&mut mgr, &glyphs, 0.0, 0.0, 5.0);
797 assert_eq!(ids.len(), 12); }
799
800 #[test]
801 fn screen_crossfade_chains() {
802 let mut mgr = TweenManager::new();
803 screen_crossfade(&mut mgr, 0.2, |_| {});
804 mgr.tick(0.25); assert!(mgr.active_count() >= 1, "Should have started fade-in");
806 }
807
808 #[test]
809 fn score_roll_up_named() {
810 let mut mgr = TweenManager::new();
811 score_roll_up(&mut mgr, 1000.0, 1.0);
812 mgr.tick(0.5);
813 let val = mgr.get_named("score_display");
814 assert!(val > 0.0 && val < 1000.0);
815 }
816}