water_drop_progress 1.0.0 copy "water_drop_progress: ^1.0.0" to clipboard
water_drop_progress: ^1.0.0 copied to clipboard

A customizable animated water-drop progress indicator with smooth liquid waves and animated fill levels.

Water Drop Progress #

A customizable animated water-drop progress indicator for Flutter.

Use it to display hydration levels, water tank levels, upload progress, download progress, goal completion, and other percentage-based values with a smooth liquid-wave animation.

Preview #

[Water Drop Progress Demo]

Features #

  • Animated water level
  • Smooth wave movement
  • Custom gradients
  • Percentage display
  • Custom overlay content
  • Smooth progress transitions
  • Configurable wave amplitude and wavelength
  • Custom border and shadow styles
  • Custom empty-drop background
  • Optional percentage formatter
  • Accessibility support
  • No third-party runtime dependencies
  • Works with any state-management solution

Installation #

Add the package to your pubspec.yaml:

dependencies:
  water_drop_progress: ^1.0.0

Then run:

flutter pub get

Import #

import 'package:water_drop_progress/water_drop_progress.dart';

Basic Usage #

WaterDropProgress(
  value: 0.50,
  width: 160,
  height: 180,
)

The value represents progress between 0.0 and 1.0:

0.0 // Empty
0.5 // 50%
1.0 // Full

Values lower than 0.0 or greater than 1.0 are automatically clamped.

Hydration Tracker Example #

final int consumed = 1250;
final int dailyGoal = 2500;

final double progress = dailyGoal > 0
    ? (consumed / dailyGoal).clamp(0.0, 1.0)
    : 0.0;

Use the calculated progress:

WaterDropProgress(
  value: progress,
  width: 160,
  height: 180,
)

Show Custom Content #

When child is provided, it replaces the default percentage text.

WaterDropProgress(
  value: progress,
  width: 160,
  height: 180,
  child: Column(
    mainAxisSize: MainAxisSize.min,
    children: [
      Text(
        '$consumed mL',
        style: const TextStyle(
          color: Colors.white,
          fontSize: 22,
          fontWeight: FontWeight.bold,
        ),
      ),
      const SizedBox(height: 4),
      Text(
        'of $dailyGoal mL',
        style: const TextStyle(
          color: Colors.white,
          fontSize: 12,
        ),
      ),
    ],
  ),
)

Custom Gradient #

WaterDropProgress(
  value: 0.70,
  waterGradient: const LinearGradient(
    begin: Alignment.topCenter,
    end: Alignment.bottomCenter,
    colors: [
      Color(0xFF74EBD5),
      Color(0xFF35B7C9),
      Color(0xFF147D92),
    ],
  ),
)

Disable Wave Animation #

WaterDropProgress(
  value: 0.60,
  animateWave: false,
)

Disable Level Animation #

WaterDropProgress(
  value: 0.60,
  animateLevel: false,
)

Hide Percentage #

WaterDropProgress(
  value: 0.60,
  showPercentage: false,
)

Customize Percentage Style #

WaterDropProgress(
  value: 0.75,
  percentageStyle: const TextStyle(
    color: Colors.white,
    fontSize: 28,
    fontWeight: FontWeight.w800,
  ),
)

Customize Percentage Text #

WaterDropProgress(
  value: 0.75,
  percentageFormatter: (value) {
    return '${(value * 2500).round()} mL';
  },
)

Customize Wave #

WaterDropProgress(
  value: 0.65,
  waveAmplitude: 0.05,
  waveLength: 0.90,
  waveAnimationDuration: const Duration(
    milliseconds: 1400,
  ),
)

Customize Level Animation #

WaterDropProgress(
  value: 0.80,
  levelAnimationDuration: const Duration(
    milliseconds: 900,
  ),
  levelCurve: Curves.easeInOutCubic,
)

Customize Border and Background #

WaterDropProgress(
  value: 0.75,
  emptyColor: const Color(0xFFF5F7FA),
  borderColor: const Color(0xFFE7EAF0),
  innerBorderColor: const Color(0xFFD9DEE8),
  borderWidth: 8,
  innerBorderWidth: 3,
)

Customize Shadow #

WaterDropProgress(
  value: 0.65,
  shadowColor: Colors.black26,
  shadowElevation: 12,
)

Accessibility #

WaterDropProgress(
  value: 0.60,
  semanticLabel: 'Daily hydration progress',
)

Animation Completion Callback #

WaterDropProgress(
  value: 0.85,
  onLevelAnimationEnd: () {
    debugPrint('Water level animation completed');
  },
)

Complete Example #

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

void main() {
  runApp(const ExampleApp());
}

class ExampleApp extends StatelessWidget {
  const ExampleApp({super.key});

  @override
  Widget build(BuildContext context) {
    return const MaterialApp(
      debugShowCheckedModeBanner: false,
      home: WaterDropExampleScreen(),
    );
  }
}

class WaterDropExampleScreen extends StatefulWidget {
  const WaterDropExampleScreen({super.key});

  @override
  State<WaterDropExampleScreen> createState() {
    return _WaterDropExampleScreenState();
  }
}

class _WaterDropExampleScreenState
    extends State<WaterDropExampleScreen> {
  double progress = 0.50;

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: const Text('Water Drop Progress'),
        centerTitle: true,
      ),
      body: SafeArea(
        child: Center(
          child: Padding(
            padding: const EdgeInsets.all(24),
            child: Column(
              mainAxisAlignment: MainAxisAlignment.center,
              children: [
                WaterDropProgress(
                  value: progress,
                  width: 170,
                  height: 200,
                ),
                const SizedBox(height: 24),
                Text(
                  '${(progress * 2500).round()} mL',
                  style: const TextStyle(
                    fontSize: 24,
                    fontWeight: FontWeight.w800,
                  ),
                ),
                const SizedBox(height: 4),
                const Text(
                  'Daily goal: 2500 mL',
                ),
                const SizedBox(height: 24),
                Slider(
                  value: progress,
                  min: 0,
                  max: 1,
                  divisions: 100,
                  label: '${(progress * 100).round()}%',
                  onChanged: (double value) {
                    setState(() {
                      progress = value;
                    });
                  },
                ),
              ],
            ),
          ),
        ),
      ),
    );
  }
}

Main Parameters #

Parameter Type Default Description
value double Required Progress value from 0.0 to 1.0
width double 160 Drop width
height double 180 Drop height
animateLevel bool true Animates water-level changes
animateWave bool true Enables continuous wave movement
levelAnimationDuration Duration 700ms Duration of water-level animation
waveAnimationDuration Duration 1600ms Duration of one wave cycle
levelCurve Curve easeInOutCubic Curve used for level changes
waveAmplitude double 0.04 Wave height relative to drop height
waveLength double 0.85 Wave length relative to drop width
waterGradient Gradient Blue gradient Water fill gradient
emptyColor Color Light grey Empty-drop background
borderColor Color Light grey Outer border color
innerBorderColor Color Light grey Inner border color
borderWidth double 8 Outer border width
innerBorderWidth double 3 Inner border width
shadowColor Color Transparent black Drop shadow color
shadowElevation double 10 Drop shadow elevation
showPercentage bool true Displays percentage text
percentageStyle TextStyle? null Custom percentage style
percentageFormatter String Function(double)? null Custom percentage formatter
child Widget? null Custom content inside the drop
semanticLabel String? null Accessibility label
onLevelAnimationEnd VoidCallback? null Called when level animation finishes

Use Cases #

  • Hydration trackers
  • Water-consumption applications
  • Water tank indicators
  • Goal-completion widgets
  • Upload progress
  • Download progress
  • Fitness and health applications
  • Environmental dashboards
  • Smart-home water monitoring
  • Onboarding and loading screens

Performance #

The widget uses CustomPainter, AnimationController, and RepaintBoundary to keep animations smooth and minimize unnecessary rebuilds.

For best performance:

  • Avoid using very large widget dimensions.
  • Disable animateWave when the widget is not visible.
  • Reuse the same widget instead of recreating it unnecessarily.
  • Keep custom overlay widgets lightweight.

Contributing #

Contributions are welcome.

You can contribute by:

  • Reporting bugs
  • Suggesting features
  • Improving documentation
  • Adding tests
  • Submitting pull requests

For major changes, open an issue first to discuss the proposed update.

Issues and Feedback #

Found a bug or have a feature request? Open an issue in the package repository.

License #

This project is licensed under the MIT License.

See the LICENSE file for complete license information.

5
likes
150
points
5
downloads

Documentation

API reference

Publisher

verified publisherjeuxtesting.com

Weekly Downloads

A customizable animated water-drop progress indicator with smooth liquid waves and animated fill levels.

Repository (GitHub)
View/report issues

Topics

#progress #animation #water #liquid #hydration

License

MIT (license)

Dependencies

flutter

More

Packages that depend on water_drop_progress