fluid_motions 0.0.3 copy "fluid_motions: ^0.0.3" to clipboard
fluid_motions: ^0.0.3 copied to clipboard

A declarative, physics-based fluid animation and gesture package for Flutter, inspired by Framer Motion.

Fluid Motions 🌊 #

Pub Version Flutter Tests License

πŸ‘‰ Try the Interactive Web Demo! πŸ‘ˆ

A declarative, physics-based animation engine for Flutter.

Say goodbye to static Durations and rigid Curves. Fluid Motions brings organic, spring-driven physics to your UI, inspired by Framer Motion.

By leveraging continuous velocity and momentum preservation, animations feel natural, interruptible, and deeply satisfyingβ€”just like real-world objects.


🌟 Why Fluid Motions? #

In traditional Flutter animations (AnimatedContainer, Tween, etc.), animations run for a hardcoded time (e.g., 300ms). If a user interrupts the animation halfway through, the object abruptly stops and restarts, killing momentum.

Fluid Motions solves this by using SpringSimulation under the hood:

  • Physics, not durations: Animations finish when they naturally settle, based on Mass, Stiffness, and Damping.
  • Momentum Preservation: Interrupting an animation mid-flight redirects it smoothly, conserving its current velocity.
  • True Overshoot: Elements can organically stretch past their bounds (bouncing) without complex curve math.

πŸ“¦ Installation #

Add the dependency to your pubspec.yaml:

dependencies:
  fluid_motions: ^0.0.1 # Check pub.dev for the latest version

πŸš€ Quick Start #

Replace your traditional AnimatedContainer with FluidContainer. Notice you don't need to pass any durations!

import 'package:flutter/material.dart';
import 'package:fluid_motions/fluid_motions.dart';

class MyFluidWidget extends StatefulWidget {
  @override
  _MyFluidWidgetState createState() => _MyFluidWidgetState();
}

class _MyFluidWidgetState extends State<MyFluidWidget> {
  bool _isActive = false;

  @override
  Widget build(BuildContext context) {
    return GestureDetector(
      onTap: () => setState(() => _isActive = !_isActive),
      child: FluidContainer(
        isActive: _isActive,
        // 1. Define your physics (or use factories like .bouncy() / .smooth())
        springConfig: FluidSpringConfig.bouncy(),
        // 2. Define the inactive state
        inactiveDecoration: BoxDecoration(
          color: Colors.blue,
          borderRadius: BorderRadius.circular(16),
        ),
        // 3. Define the active state
        activeDecoration: BoxDecoration(
          color: Colors.red,
          borderRadius: BorderRadius.circular(100),
        ),
        child: const SizedBox(
          width: 200, 
          height: 200, 
          child: Center(child: Text('Tap Me!', style: TextStyle(color: Colors.white))),
        ),
      ),
    );
  }
}

βš™οΈ Core Concepts #

FluidSpringConfig #

The heart of the physics engine. It takes three parameters:

  • mass: The weight of the object. Heavier objects are harder to move and stop.
  • stiffness: The tension of the spring. Higher values make the animation snappier and faster.
  • damping: The friction. Higher values reduce bounce, stopping the spring faster.
// Pre-built factories for convenience:
final bouncy = FluidSpringConfig.bouncy();
final smooth = FluidSpringConfig.smooth();

// Or create your own custom physics:
final custom = FluidSpringConfig(mass: 1.0, stiffness: 120.0, damping: 15.0);

FluidInteractable (New & Magical ✨) #

Add Apple-like physical interactions to any button, card, or icon instantly. It automatically tracks Hover and Tap gestures, and animates its scale and position using continuous spring physics. Say goodbye to manual state management!

FluidInteractable(
  onTap: () => print("Tapped!"),
  scaleOnHover: 1.05,  // Grow smoothly on mouse hover
  scaleOnTap: 0.90,    // Shrink organically on tap
  offsetOnHover: const Offset(0, -5), // Elevate on hover
  springConfig: FluidSpringConfig.bouncy(),
  child: Container(
    padding: const EdgeInsets.all(16),
    color: Colors.deepPurple,
    child: const Text("Interact With Me", style: TextStyle(color: Colors.white)),
  ),
)

FluidContainer #

A declarative widget that morphs its BoxDecoration between inactiveDecoration and activeDecoration smoothly using physics when isActive changes.

🀝 Contributing #

Contributions are welcome! Feel free to open issues or submit Pull Requests to add more fluid widgets (like FluidTransform, FluidFade, etc.).

πŸ“„ License #

This project is licensed under the MIT License - see the LICENSE file for details.

2
likes
0
points
136
downloads

Publisher

verified publisherpauloriveiro.com

Weekly Downloads

A declarative, physics-based fluid animation and gesture package for Flutter, inspired by Framer Motion.

Repository (GitHub)
View/report issues

License

unknown (license)

Dependencies

flutter

More

Packages that depend on fluid_motions