How to update the progress color of CircularPercentIndicator programatically for a given period of minutes?

358 views Asked by At

I have this component:

GestureDetector(
                onLongPress: () {
                  _startTimer();
                },
                onLongPressUp: () {
                  _timer.cancel();
                },
                onLongPressEnd: (LongPressEndDetails longPressEndDetails) {
                  _timer.cancel();
                },
                child: CircularPercentIndicator(
                  animationDuration: 200,
                  animateFromLastPercent: true,
                  radius: 150.0,
                  lineWidth: 10.0,
                  percent: _progress,
                  progressColor: Colors.red,
                  backgroundColor: Colors.white,
                  animation: true,
                  circularStrokeCap: CircularStrokeCap.butt,
                ),
              ),

And the start timer method is:

void _startTimer() {
    const oneSec = const Duration(milliseconds: 200);
    _timer = Timer.periodic(oneSec, (timer) {
      print(timer.tick.toString());
      final updated = ((_progress + 0.01).clamp(0.0, 1.0) * 100);

      print(updated.round() / 100);
      // if (_progress < 1.0)
      setState(() {
        _progress = updated.round() / 100;
      });
    });
  }

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

My question is, I want to slowly but smoothly fill the progress color, i.e update percent based on the time left. Somthing like Snapchat video recorder. I want to fill up the percent for 3 minutes lets say. I have tried to play different things but either its too not smooth or just finishes quickly. What am I doing wrong? Thanks

2

There are 2 answers

0
Sam Chan On BEST ANSWER

why not use it simply

  void _startTimer() {
    if (_progress < 1) {
      const oneSec = const Duration(milliseconds: 200);
      _timer = Timer.periodic(oneSec, (timer) {
        setState(() {
          _progress = min(_progress + (200 / (3 * 60 * 1000)), 1);
        });
      });
    }
  }
1
Vivek Shetty On

Hey your code _startTimer() funtion looks fine but your onlclick has issue, have updated your code try this

GestureDetector(
   onTap: () {
     _startTimer();
              },
              child: CircularPercentIndicator(
                animationDuration: 200,
                animateFromLastPercent: true,
                radius: 50.0,
                lineWidth: 10.0,
                percent: _progress,
                progressColor: Colors.red,
                backgroundColor: Colors.blue,
                animation: true,
                circularStrokeCap: CircularStrokeCap.butt,
              ),
            )

void _startTimer() {
    const oneSec = const Duration(milliseconds: 200);
    _timer = Timer.periodic(oneSec, (timer) {
      if(_progress==1.0)_timer.cancel();
      final updated = ((_progress + 0.01).clamp(0.0, 1.0) * 100);
      setState(() {
        _progress = updated.round() / 100;
      });
    });
  }