Flutter ListView Click Option Animation

Flutter ListView Click Option Animation:This Flutter Tutorial post is you can implement your application, ListView Click open the animation options edit, update, delete.This Flutter Tutorial post lib, 3 page available. main.dart, country_page.dart, country_item.dart.
Country_item.dart one of widget Positioned.fill() search change the background color option menu.

Flutter ListView Click Option Animation
Flutter ListView Click Option Animation

Flutter ListView Click Option Animation :

main.dart

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

void main() => runApp(MyApp());

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      title: 'Flutter Tutorial',
      theme: ThemeData(
        primarySwatch: Colors.blue,
      ),
      debugShowCheckedModeBanner: false,
      home: CountryPage(),
    );
  }
}

country_page.dart

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

class CountryPage extends StatefulWidget {
  @override
  _CountryState createState() => _CountryState();
}

class _CountryState extends State<CountryPage> with SingleTickerProviderStateMixin {
  Animation<double> _animation;
  AnimationController _controller;
  int selectIndex = -1;

  final europeanCountries = [
    'Albania',
    'Andorra',
    'Armenia',
    'Austria',
    'Azerbaijan',
    'Belarus',
    'Belgium',
    'Bosnia and Herzegovina',
    'Bulgaria',
    'Croatia',
    'Cyprus',
    'Czech Republic',
    'Denmark',
    'Estonia',
    'Finland',
    'France',
    'Georgia',
    'Germany',
    'Greece',
    'Hungary',
    'Iceland',
    'Ireland',
    'Italy',
    'Kazakhstan',
    'Kosovo',
    'Latvia',
    'Liechtenstein',
    'Lithuania',
    'Luxembourg',
    'Macedonia',
    'Malta',
    'Moldova',
    'Monaco',
    'Montenegro',
    'Netherlands',
    'Norway',
    'Poland',
    'Portugal',
    'Romania',
    'Russia',
    'San Marino',
    'Serbia',
    'Slovakia',
    'Slovenia',
    'Spain',
    'Sweden',
    'Switzerland',
    'Turkey',
    'Ukraine',
    'United Kingdom',
    'Vatican City'
  ];
  @override
  void initState() {
    super.initState();

    _controller = new AnimationController(
        duration: const Duration(milliseconds: 450), vsync: this);
    CurvedAnimation _curvedAnimation =
        CurvedAnimation(parent: _controller, curve: Curves.easeOutSine);
    _animation = new Tween(begin: 0.0, end: 1.1).animate(_curvedAnimation);
  }

  @override
  void dispose() {
    super.dispose();
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
        appBar: AppBar(
            title: Text('Flutter Tutorial'),
            brightness: Brightness.light,
            elevation: 0.0,
            backgroundColor: Colors.blue),

        body: ListView.builder(
          itemCount: europeanCountries.length,
          itemBuilder: (context, index) {
            return CountryItem(
              index: index,
              selectIndex: this.selectIndex,
              name: europeanCountries[index],
              animation: _animation,
              onTapMenu: () {
                _controller.forward(from: 0.0);
                setState(() {
                  selectIndex = index;
                });
              },
              onTapMenuClose: () {
                _controller.reverse(from: 1.1);
              },
              onTapEdit: () {},
              onTapOperation: () {},
              onTapDelete: () {
                _controller.reverse(from: 1.1);
              },
            );
          },
        ));
  }
}

country_item.dart

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

class CountryItem extends StatelessWidget {
  const CountryItem(
      {Key key,
      @required this.name,
      @required this.index,
      @required this.selectIndex,
      @required this.onTapMenu,
      @required this.onTapEdit,
      @required this.onTapOperation,
      @required this.onTapDelete,
      @required this.onTapMenuClose,
      @required this.animation})
      : super(key: key);

  final String name;
  final int index;
  final int selectIndex;
  final Function onTapMenu;
  final Function onTapEdit;
  final Function onTapOperation;
  final Function onTapDelete;
  final Function onTapMenuClose;
  final Animation<double> animation;

  @override
  Widget build(BuildContext context) {
    return Stack(
      children: <Widget>[
        Container(
          padding: const EdgeInsets.only(left: 16.0, top: 16.0),
          child: DecoratedBox(
            decoration: BoxDecoration(
                border: Border(
              bottom: Divider.createBorderSide(context,
                  color: Colors.orange, width: 0.8),
            )),
            child: Padding(
              padding: const EdgeInsets.only(right: 16.0, bottom: 16.0),
              child: Row(
                crossAxisAlignment: CrossAxisAlignment.start,
                children: <Widget>[
                  Expanded(
                    child: Column(
                      crossAxisAlignment: CrossAxisAlignment.start,
                      children: <Widget>[
                        Text(
                          name,
                          maxLines: 1,
                          style: TextStyle(fontSize: 16),
                          overflow: TextOverflow.ellipsis,
                        ),
                        SizedBox(height: 5),
                        Row(
                          children: <Widget>[
                            Container(
                              child: const Text(
                                "Country Description",
                                style: TextStyle(
                                  color: Colors.black54,
                                ),
                              ),
                            ),
                          ],
                        ),
                        SizedBox(height: 2),
                        Offstage(
                          offstage: index % 3 != 0,
                          child: Container(
                            decoration: BoxDecoration(
                              borderRadius: BorderRadius.circular(2.0),
                            ),
                            alignment: Alignment.topLeft,
                            child: const Text(
                              "Flutter tutorial provide daily new post.",
                              style: TextStyle(
                                color: Colors.grey,
                              ),
                            ),
                          ),
                        ),
                      ],
                    ),
                  ),
                  Column(
                    crossAxisAlignment: CrossAxisAlignment.end,
                    children: <Widget>[
                      GestureDetector(
                        child: Container(
                            height: 24.0,
                            padding:
                            EdgeInsets.only(left: 8.0, bottom: 8.0),
                            child: Text('Click', style:TextStyle(color: Colors.blue))),
                        onTap: onTapMenu,
                      ),
                      SizedBox(height: 10),
                      Padding(
                        padding: const EdgeInsets.only(top: 30.0),
                        child: Text(
                          "Flutter Tutorial", style:TextStyle(color: Colors.grey.withOpacity(0.8)),
                        ),
                      )
                    ],
                  )
                ],
              ),
            ),
          ),
        ),
        Positioned.fill(
          child: Offstage(
            offstage: selectIndex != index,
            child: AnimatedBuilder(
                animation: animation,
                builder: (_, child) {
                  return MenuReveal(
                    revealPercent: animation.value,
                    child: InkWell(
                      onTap: onTapMenuClose,
                      child: Container(
                        color: Colors.blue.withOpacity(0.1), //Color(0x4D000000),
                        child: Theme(
                          data: Theme.of(context).copyWith(
                            buttonTheme: ButtonThemeData(
                              padding:
                                  const EdgeInsets.symmetric(horizontal: 12.0),
                              minWidth: 70.0,
                              height: 35.0,
                              materialTapTargetSize:
                                  MaterialTapTargetSize.shrinkWrap, // 距顶部距离为0
                              shape: RoundedRectangleBorder(
                                borderRadius: BorderRadius.circular(24.0),
                              ),
                            ),
                            textTheme: const TextTheme(button: TextStyle()),
                          ),
                          child: Row(
                            mainAxisAlignment: MainAxisAlignment.spaceEvenly,
                            children: <Widget>[
                              FlatButton(
                                color: Colors.white,
                                child: const Text("Edit"),
                                onPressed: onTapOperation,
                              ),
                              FlatButton(
                                color: Colors.white,
                                child: const Text("Update"),
                                onPressed: onTapOperation,
                              ),
                              FlatButton(
                                color: Colors.white,
                                child: const Text("Delete"),
                                onPressed: onTapDelete,
                              ),
                            ],
                          ),
                        ),
                      ),
                    ),
                  );
                }),
          ),
        )
      ],
    );
  }
}

class MenuReveal extends StatelessWidget {
  final double revealPercent;
  final Widget child;

  MenuReveal({this.revealPercent, this.child});

  @override
  Widget build(BuildContext context) {
    return ClipOval(
      clipper: new CircleRevealClipper(revealPercent),
      child: child,
    );
  }
}

class CircleRevealClipper extends CustomClipper<Rect> {
  final double revealPercent;
  CircleRevealClipper(this.revealPercent);

  @override
  Rect getClip(Size size) {
    final epicenter = new Offset(size.width - 25.0, 25.0);

    double theta = atan(epicenter.dy / epicenter.dx);
    final distanceToCorner = (epicenter.dy) / sin(theta);

    final radius = distanceToCorner * revealPercent;
    final diameter = 2 * radius;

    return new Rect.fromLTWH(
        epicenter.dx - radius, epicenter.dy - radius, diameter, diameter);
  }

  @override
  bool shouldReclip(CustomClipper<Rect> oldClipper) {
    return true;
  }
}

The flutter tutorial  is a website that bring you the latest and amazing resources of code. All the languages codes are included in this website. The languages like flutter, android, java,kotlin etc.with the help of this languages any user can develop the beautiful application

For more information about Flutter. visit www.fluttertutorial.in