flutterfx_orbit_blur 1.1.0 copy "flutterfx_orbit_blur: ^1.1.0" to clipboard
flutterfx_orbit_blur: ^1.1.0 copied to clipboard

A Flutter widget that renders two orbiting icon rings with a frosted-glass blur center. Part of the FlutterFX collection of animated widgets.

example/lib/main.dart

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

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

// ─── Preset definitions ────────────────────────────────────────────────────

class _Preset {
  final String label;
  final Color bg;
  final OrbitStyle style;
  final List<IconData>? leftIcons;
  final List<IconData>? rightIcons;
  final List<Widget>? leftWidgets;
  final List<Widget>? rightWidgets;

  const _Preset({
    required this.label,
    required this.bg,
    required this.style,
    this.leftIcons,
    this.rightIcons,
    this.leftWidgets,
    this.rightWidgets,
  });
}

final _presets = [
  // 1 ── Default dark
  const _Preset(
    label: 'Dark (default)',
    bg: Colors.black,
    style: OrbitStyle.dark(),
  ),

  // 2 ── Light preset
  const _Preset(
    label: 'Light',
    bg: Color(0xFFF0F0F0),
    style: OrbitStyle.light(),
  ),

  // 3 ── Amber / custom colors
  _Preset(
    label: 'Amber',
    bg: const Color(0xFF1A1200),
    style: OrbitStyle(
      iconColor: Colors.amber,
      iconContainerColor: Colors.amber.withValues(alpha: 0.15),
      iconContainerBorderColor: Colors.amber.withValues(alpha: 0.4),
      orbitPathColor: Colors.amber.withValues(alpha: 0.15),
      centerBlurSigma: 10,
      centerColor: Colors.amber.withValues(alpha: 0.2),
      centerWidget: const Icon(Icons.bolt, color: Colors.amber, size: 26),
    ),
    leftIcons: const [Icons.bolt, Icons.star, Icons.local_fire_department],
    rightIcons: const [Icons.sunny, Icons.flash_on, Icons.auto_awesome],
  ),

  // 4 ── Purple / custom center widget
  _Preset(
    label: 'Purple',
    bg: const Color(0xFF0D001A),
    style: OrbitStyle(
      iconColor: Colors.purpleAccent,
      iconContainerColor: Colors.purple.withValues(alpha: 0.2),
      iconContainerBorderColor: Colors.purpleAccent.withValues(alpha: 0.5),
      orbitPathColor: Colors.purpleAccent.withValues(alpha: 0.15),
      centerBlurSigma: 14,
      centerColor: Colors.purpleAccent.withValues(alpha: 0.2),
      centerWidget: const Icon(Icons.rocket_launch,
          color: Colors.purpleAccent, size: 26),
    ),
    leftIcons: const [Icons.stars, Icons.auto_awesome, Icons.bubble_chart],
    rightIcons: const [Icons.diamond, Icons.hexagon, Icons.blur_on],
  ),

  // 5 ── Custom widgets (emoji + badge)
  _Preset(
    label: 'Custom widgets',
    bg: const Color(0xFF0A0A1A),
    style: OrbitStyle(
      centerBlurSigma: 8,
      centerColor: Colors.blueAccent.withValues(alpha: 0.2),
      centerWidget: const Text('⚡', style: TextStyle(fontSize: 22)),
    ),
    leftWidgets: const [
      _EmojiOrb(emoji: '🚀'),
      _EmojiOrb(emoji: '⭐'),
      _EmojiOrb(emoji: '🔥'),
    ],

    rightWidgets: const [
      _ColorBadge(color: Colors.redAccent, label: 'R'),
      _ColorBadge(color: Colors.greenAccent, label: 'G'),
      _ColorBadge(color: Colors.blueAccent, label: 'B'),
    ],
  ),
];

// ─── App ───────────────────────────────────────────────────────────────────

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

  @override
  State<OrbitBlurExample> createState() => _OrbitBlurExampleState();
}

class _OrbitBlurExampleState extends State<OrbitBlurExample> {
  int _presetIndex = 0;
  bool _reverse = true;
  bool _showPaths = true;
  double _duration = 10.0;

  _Preset get _preset => _presets[_presetIndex];

  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      debugShowCheckedModeBanner: false,
      home: AnimatedContainer(
        duration: const Duration(milliseconds: 400),
        color: _preset.bg,
        child: Scaffold(
          backgroundColor: Colors.transparent,
          body: Center(
            child: SingleChildScrollView(
              padding: const EdgeInsets.symmetric(vertical: 32),
              child: Column(
                mainAxisAlignment: MainAxisAlignment.center,
                children: [
                  // ── Widget ────────────────────────────────────────────
                  OrbitingIcons(
                    reverse: _reverse,
                    duration: _duration,
                    showPaths: _showPaths,
                    style: _preset.style,
                    leftIcons: _preset.leftIcons,
                    rightIcons: _preset.rightIcons,
                    leftWidgets: _preset.leftWidgets,
                    rightWidgets: _preset.rightWidgets,
                  ),

                  const SizedBox(height: 40),

                  // ── Preset picker ──────────────────────────────────────
                  Wrap(
                    spacing: 8,
                    runSpacing: 8,
                    alignment: WrapAlignment.center,
                    children: List.generate(_presets.length, (i) {
                      final selected = i == _presetIndex;
                      return GestureDetector(
                        onTap: () => setState(() => _presetIndex = i),
                        child: AnimatedContainer(
                          duration: const Duration(milliseconds: 200),
                          padding: const EdgeInsets.symmetric(
                              horizontal: 14, vertical: 7),
                          decoration: BoxDecoration(
                            color: selected
                                ? Colors.white.withValues(alpha: 0.2)
                                : Colors.white.withValues(alpha: 0.06),
                            borderRadius: BorderRadius.circular(20),
                            border: Border.all(
                              color: selected
                                  ? Colors.white.withValues(alpha: 0.6)
                                  : Colors.white.withValues(alpha: 0.15),
                            ),
                          ),
                          child: Text(
                            _presets[i].label,
                            style: TextStyle(
                              color: Colors.white.withValues(
                                  alpha: selected ? 1.0 : 0.5),
                              fontSize: 12,
                              fontWeight: selected
                                  ? FontWeight.w600
                                  : FontWeight.normal,
                            ),
                          ),
                        ),
                      );
                    }),
                  ),

                  const SizedBox(height: 28),

                  // ── Controls ───────────────────────────────────────────
                  _Row(
                    label: 'Reverse direction',
                    child: Switch(
                      value: _reverse,
                      onChanged: (v) => setState(() => _reverse = v),
                    ),
                  ),
                  _Row(
                    label: 'Show orbit paths',
                    child: Switch(
                      value: _showPaths,
                      onChanged: (v) => setState(() => _showPaths = v),
                    ),
                  ),
                  _Row(
                    label: 'Speed: ${_duration.round()}s / orbit',
                    child: SizedBox(
                      width: 160,
                      child: Slider(
                        value: _duration,
                        min: 3,
                        max: 20,
                        divisions: 17,
                        onChanged: (v) => setState(() => _duration = v),
                      ),
                    ),
                  ),
                ],
              ),
            ),
          ),
        ),
      ),
    );
  }
}

// ─── Custom orbit item widgets ─────────────────────────────────────────────

class _EmojiOrb extends StatelessWidget {
  final String emoji;
  const _EmojiOrb({required this.emoji});

  @override
  Widget build(BuildContext context) =>
      Text(emoji, style: const TextStyle(fontSize: 20));
}

class _ColorBadge extends StatelessWidget {
  final Color color;
  final String label;
  const _ColorBadge({required this.color, required this.label});

  @override
  Widget build(BuildContext context) {
    return Container(
      width: 28,
      height: 28,
      decoration: BoxDecoration(color: color, shape: BoxShape.circle),
      alignment: Alignment.center,
      child: Text(label,
          style: const TextStyle(
              color: Colors.black, fontWeight: FontWeight.bold, fontSize: 12)),
    );
  }
}

// ─── Layout helper ─────────────────────────────────────────────────────────

class _Row extends StatelessWidget {
  final String label;
  final Widget child;
  const _Row({required this.label, required this.child});

  @override
  Widget build(BuildContext context) {
    return Padding(
      padding: const EdgeInsets.symmetric(horizontal: 32, vertical: 2),
      child: Row(
        mainAxisAlignment: MainAxisAlignment.spaceBetween,
        children: [
          Text(label,
              style:
                  const TextStyle(color: Colors.white70, fontSize: 13)),
          child,
        ],
      ),
    );
  }
}
1
likes
150
points
0
downloads
screenshot

Documentation

API reference

Publisher

unverified uploader

Weekly Downloads

A Flutter widget that renders two orbiting icon rings with a frosted-glass blur center. Part of the FlutterFX collection of animated widgets.

Topics

#animation #ui #widget #orbit

License

MIT (license)

Dependencies

flutter

More

Packages that depend on flutterfx_orbit_blur