【问题标题】:Circular progress button based on hold (flutter)基于保持(颤动)的圆形进度按钮
【发布时间】:2019-04-24 18:31:44
【问题描述】:

我正在尝试制作一个按钮,当用户按住它时,会有一个进度,但如果用户在完成之前松开按钮,进度会减少。有点像图片上的那个

【问题讨论】:

    标签: dart flutter


    【解决方案1】:

    正如 Arnold Parge 所说,您可以使用 GestureDetector 并收听 onTapDownonTapUp。要创建所需的 LoadingButton,您可以使用以下 Widget 结构:

    - GetureDetector
      - Stack
        - CircularProgressIndicator // background circle
        - CircularProgressIndicator // foreground circle
        - Icon
    

    要创建动画,您可以添加AnimationController 并将前景CircularProgressIndicator 的值绑定到AnimationController.value。现在您只需将两个侦听器添加到GestureDetector

    • onTapDown:点击按钮时,动画应该开始。因此我们调用AnimationController.forward()
    • onTapUp: 释放新闻时,我们想检查动画是否已经完成。我们可以使用AnimationController.status 来检查状态。如果是AnimationStatus.forward,它仍在运行。因此我们想通过调用AnimationController.reverse()来反转动画。

    这是生成的按钮:

    以及完整源代码:

    import 'package:flutter/material.dart';
    
    void main() => runApp(MyApp());
    
    class MyApp extends StatelessWidget {
      @override
      Widget build(BuildContext context) {
        return MaterialApp(
          theme: ThemeData(),
          home: Scaffold(
            body: Center(child: LoadingButton()),
          ),
        );
      }
    }
    
    class LoadingButton extends StatefulWidget {
      @override
      LoadingButtonState createState() => LoadingButtonState();
    }
    
    class LoadingButtonState extends State<LoadingButton>
        with SingleTickerProviderStateMixin {
      AnimationController controller;
    
      @override
      void initState() {
        super.initState();
    
        controller =
            AnimationController(vsync: this, duration: Duration(seconds: 1));
        controller.addListener(() {
          setState(() {});
        });
      }
    
      @override
      Widget build(BuildContext context) {
        return GestureDetector(
          onTapDown: (_) => controller.forward(),
          onTapUp: (_) {
            if (controller.status == AnimationStatus.forward) {
              controller.reverse();
            }
          },
          child: Stack(
            alignment: Alignment.center,
            children: <Widget>[
              CircularProgressIndicator(
                value: 1.0,
                valueColor: AlwaysStoppedAnimation<Color>(Colors.grey),
              ),
              CircularProgressIndicator(
                value: controller.value,
                valueColor: AlwaysStoppedAnimation<Color>(Colors.blue),
              ),
              Icon(Icons.add)
            ],
          ),
        );
      }
    }
    

    【讨论】:

    • 可能有点晚了,但是在点击过程中完成进度后如何触发它?因为现在我只能在用户点击按钮时触发它。
    • @ali 您还可以向onTapDown 处理程序添加条件。如果我没有正确回答您的问题,您介意具体说明您真正需要什么吗? :)
    • 正如 Ali 所问,一旦 CircularProgressIndicator 已填充且动画已完成,任何人都可以提示如何启动代码吗?非常感激!我在 onTapDown 中添加了以下内容: if(controller.status == AnimationStatus.completed) { setState(() { _theValue = "FINISHED"; }); } 不会触发。
    • 没关系,我在 Widget Build 中放置了一个变量并捕获了它:) String _theValue = controller.value.toString();
    【解决方案2】:

    使用GestureDetector

    onTapDown开始进度,如果进度不完整或者你的条件是什么,在onTapUp反转进度。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2020-05-24
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多