agentsclimarketplace

Animation patterns

Skill choxos/MathVizAgent/plugins/mathviz/skills/animation-patterns

Install
npx -y skills add choxos/MathVizAgent --skill animation-patterns

Assembled from the repository path, not quoted from the project. Check it against their README if it does not work.

One thing to look at

  • 1 stars1 stars. Stars are a popularity signal and not a quality one, but at this level it is likely that nobody has read this closely except its author, and you would be relying on your own review.

What its author says it does

Copied from the file, not written here

Production animation patterns including reveal, transform, progressive reveal, emphasis, and cleanup patterns.

SKILL.md

7.1 KB, as published. Nobody here has run it

Animation Patterns

Production-quality animation patterns for mathematical visualizations.

Reveal Patterns

Simple Reveal

# Text/formulas
self.play(Write(text), run_time=1.5)
self.wait(1)

# Shapes
self.play(Create(shape), run_time=1)

# With fill
self.play(DrawBorderThenFill(shape), run_time=1.5)

Dramatic Entrance

# Grow from center
self.play(GrowFromCenter(obj), run_time=1.5)

# Grow from edge
self.play(GrowFromEdge(obj, LEFT), run_time=1)

# Spin in
self.play(SpinInFromNothing(obj), run_time=1.5)

Fade Variants

# Simple fade
self.play(FadeIn(obj))

# With direction
self.play(FadeIn(obj, shift=UP))
self.play(FadeIn(obj, shift=DOWN * 0.5))

# Scale fade
self.play(FadeIn(obj, scale=0.5))  # Grow while fading in

Transform Patterns

Basic Transform

# Morph A into B (A still exists, looks like B)
self.play(Transform(a, b))

# Replace A with B (A is removed, B is added)
self.play(ReplacementTransform(a, b))

# Cross-fade
self.play(FadeTransform(a, b))

Matching Transforms

# Match shapes between mobjects
self.play(TransformMatchingShapes(text1, text2))

# Match TeX parts
eq1 = MathTex("a", "+", "b", "=", "c")
eq2 = MathTex("a", "=", "c", "-", "b")
self.play(TransformMatchingTex(eq1, eq2))

Staged Transform

# Transform in stages
self.play(a.animate.move_to(b.get_center()))
self.play(Transform(a, b))

# Or animate properties first
self.play(a.animate.set_color(b.get_color()))
self.play(Transform(a, b))

Progressive Reveal Patterns

LaggedStart

# Stagger multiple animations
elements = [Circle(), Square(), Triangle()]

self.play(LaggedStart(
    *[Create(e) for e in elements],
    lag_ratio=0.3  # 30% overlap
), run_time=3)

LaggedStartMap

# Cleaner syntax for same animation type
group = VGroup(Circle(), Square(), Triangle())

self.play(LaggedStartMap(
    Create,           # Animation class
    group,            # Target group
    lag_ratio=0.2
), run_time=2)

# With extra parameters
self.play(LaggedStartMap(
    FadeIn,
    group,
    lag_ratio=0.1,
    shift=UP * 0.5    # Each element fades in from below
), run_time=2)

Progressive Data Points

# Add points progressively
points = VGroup(*[Dot(axes.c2p(x, y)) for x, y in data])

# Fast progressive reveal
self.play(LaggedStart(
    *[FadeIn(p, scale=0.5) for p in points],
    lag_ratio=0.02
), run_time=3)

Sequential Section Reveal

# Reveal formula parts
formula = MathTex("y", "=", "m", "x", "+", "b")

self.play(Write(formula[0:2]))  # "y ="
self.wait(0.5)
self.play(Write(formula[2:4]))  # "mx"
self.wait(0.5)
self.play(Write(formula[4:]))   # "+ b"

Emphasis Patterns

Indicate

# Temporary highlight
self.play(Indicate(obj))
self.play(Indicate(obj, color=YELLOW))
self.play(Indicate(obj, scale_factor=1.2))

Circumscribe

# Draw outline around object
self.play(Circumscribe(obj))
self.play(Circumscribe(obj, color=RED))
self.play(Circumscribe(obj, shape=Rectangle))

Flash

# Brief flash effect
self.play(Flash(obj))
self.play(Flash(obj, color=YELLOW, flash_radius=0.5))

FocusOn

# Draw attention with pulse
self.play(FocusOn(obj))
self.play(FocusOn(point))

Wiggle

# Shake object
self.play(Wiggle(obj))

Combined Emphasis

# For critical insights
def emphasize(self, obj):
    self.play(Indicate(obj, color=YELLOW))
    self.play(Circumscribe(obj, color=YELLOW))
    self.play(Flash(obj))
    self.wait(2)

Cleanup Patterns

Explicit Tracking

class MyScene(Scene):
    def setup(self):
        self.tracked = []

    def track(self, *mobjects):
        for m in mobjects:
            self.tracked.append(m)
            self.add(m)
        return mobjects[0] if len(mobjects) == 1 else mobjects

    def cleanup(self, keep=None):
        keep = keep or []
        to_remove = [m for m in self.tracked if m not in keep]
        if to_remove:
            self.play(*[FadeOut(m) for m in to_remove])
        self.tracked = list(keep)

Group Cleanup

# Group related objects for easy cleanup
section1_objects = VGroup(title, subtitle, diagram)
self.play(FadeOut(section1_objects))

Transition Pattern

def transition_to_next_section(self, keep=None):
    """Fade out current section, prepare for next"""
    keep = keep or []

    # Fade out everything except kept objects
    to_remove = [m for m in self.mobjects if m not in keep]
    if to_remove:
        self.play(*[FadeOut(m) for m in to_remove], run_time=0.5)

    self.wait(0.5)

Dynamic Update Patterns

ValueTracker with always_redraw

# Create tracker
tracker = ValueTracker(0)

# Create dynamic object
dot = always_redraw(
    lambda: Dot(axes.c2p(tracker.get_value(), f(tracker.get_value())))
)

self.add(dot)

# Animate the tracker
self.play(tracker.animate.set_value(5), run_time=3)

Manual Updater

# Add updater function
def update_label(label):
    label.next_to(dot, UP)

label.add_updater(update_label)
self.add(label)

# Remove when done
label.clear_updaters()

Dynamic Area

tracker = ValueTracker(-3)

area = always_redraw(
    lambda: axes.get_area(
        graph,
        x_range=[-3, tracker.get_value()],
        color=BLUE
    )
)

self.add(area)
self.play(tracker.animate.set_value(3), run_time=4)

Composition Patterns

Simultaneous

# Multiple animations at once
self.play(
    Create(circle),
    Write(label),
    FadeIn(background)
)

Succession

# Sequential in single play call
self.play(Succession(
    Create(circle),
    Wait(0.5),
    circle.animate.set_color(RED),
    Wait(0.5),
    FadeOut(circle)
))

AnimationGroup

# Fine control over grouping
self.play(AnimationGroup(
    Create(circle),
    Create(square),
    lag_ratio=0.5,
    run_time=2
))

Best Practices

Timing Guidelines

Animation Typerun_timewait_after
Title/label1.0s0.5s
Simple shape1.0s0.5s
Formula1.5-2.0s1.0-2.0s
Complex formula2.0s4.0s
Transform1.5-2.0s1.0s
Emphasis0.5-1.0s0.5s
Data reveal2.0-3.0s1.0s

Pacing Principles

# Fast for familiar content
self.play(Write(text), run_time=0.5)

# Slow for new concepts
self.play(Write(new_formula), run_time=2)
self.wait(4)  # Time to comprehend

# Dramatic for key moments
self.play(Transform(a, b), run_time=3, rate_func=smooth)
self.play(Flash(result))
self.wait(6)  # Let it sink in

Avoid Anti-Patterns

# BAD: Too fast
self.play(Write(complex_formula), run_time=0.3)

# GOOD: Appropriate timing
self.play(Write(complex_formula), run_time=2)
self.wait(4)

# BAD: No breathing room
self.play(anim1)
self.play(anim2)
self.play(anim3)

# GOOD: Strategic pauses
self.play(anim1)
self.wait(1)
self.play(anim2)
self.wait(0.5)
self.play(anim3)

Keep looking

Skills are one crate of 328,083. Ordering is by how many stacks a row turns up in, so the top of any crate is what has actually been picked rather than what has the most stars.