0

我刚刚制作了一个动画复选框,其中颜色是动画的。这是代码:

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

class CustomCheckbox extends StatefulWidget {
  final Color activeColor;
  final Color iconColor;
  late bool isVisible = false;
  late Color backgroundColor = Colors.transparent;
  CustomCheckbox({Key? key, required this.activeColor, required this.iconColor}) : super(key: key);

  @override
  _CustomCheckboxState createState() => _CustomCheckboxState();
}

class _CustomCheckboxState extends State<CustomCheckbox> with SingleTickerProviderStateMixin {
  late AnimationController _controller;
  late Animation<Color?> _backgroundColorAnimation;
  late Animation<Color?> _iconColorAnimation;

  @override
  void initState() {
    super.initState();
    //Create the Animation Controller
    _controller = AnimationController(
      duration: const Duration(milliseconds: 300),
      vsync: this, //Refer to this widget
    );

    //Create 2 Animation for the Colors
    _backgroundColorAnimation = ColorTween(begin: Colors.transparent, end: widget.activeColor)
        .animate(_controller);
    _iconColorAnimation = ColorTween(begin: Colors.transparent, end: widget.iconColor)
        .animate(_controller);

    _controller.addListener(() {
      print (_backgroundColorAnimation.value);
    });
  }

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

  @override
  Widget build(BuildContext context) {
    return AnimatedBuilder(
      animation: _controller,
      builder: (BuildContext context, _) {
        return Container(
          decoration: BoxDecoration(
            color: _backgroundColorAnimation.value,
            border: Border.all(
              width: 0.3.w,
              color: Theme.of(context).splashColor,
            ),
            borderRadius: BorderRadius.circular(0.8.w),
          ),
          child: InkWell(
            highlightColor : Colors.transparent,
            splashColor: Colors.transparent,
            child: Visibility(
              //Maintain the space where the widget is even if it is hid
              maintainAnimation: true,
              maintainState: true,
              maintainSize: true,
              visible: widget.isVisible,
              child: Icon(
                Icons.check_outlined,
                size: 4.w,
                color: _iconColorAnimation.value,
              ),
            ),
            onTap: () {
              setState(() {

                widget.isVisible = !widget.isVisible;
                if (widget.backgroundColor == Colors.transparent){
                  widget.backgroundColor = widget.activeColor;
                  //Put the animation forward if the checkbox is unchecked
                  _controller.forward();
                } else{
                  widget.backgroundColor = Colors.transparent;
                  //Put the animation reverse if the checkbox is checked
                  _controller.reverse();
                }
              });
            },
          ),
        );
      },
    );
  }
}

我想测试颜色是否正确,所以我做了一个小部件测试来测试它:

testWidgets('CustomCheckbox Test', (WidgetTester tester) async{
    await tester.pumpWidget(Sizer(
        builder: (context, orientation, deviceType) {
          return MaterialApp(
            home: Material(
              child: CustomCheckbox(
                iconColor: Colors.purple,
                activeColor: Colors.yellow,
              )
            ),
          );
        }
    ));
    final container = tester.widget<Container>(find.byType(Container)).decoration as BoxDecoration;
    final icon = tester.widget<Icon>(find.byType(Icon));

    expect(container.color, Colors.transparent);
    expect(icon.color, Colors.transparent);
    expect(find.byIcon(Icons.check_outlined),findsOneWidget);
    await tester.tap(find.byType(InkWell));
    await tester.pump(const Duration(milliseconds: 1000));
    print(container);
    print (icon);
  });

问题是当我泵送小部件时,颜色根本没有改变,我得到了这些结果:

Testing started at 14:46 ...

Color(0x00000000)
BoxDecoration(color: Color(0x00000000), border: Border.all(BorderSide(Color(0x66c8c8c8), 1.8, BorderStyle.solid)), borderRadius: BorderRadius.circular(4.8))
Icon(IconData(U+0EF49), size: 24.0, color: Color(0x00000000))
Color(0x00000000)

似乎动画只迭代了2次,我不知道为什么......

感谢您的建议!

克里斯

4

0 回答 0