1

I need to build a custom timer with rounded rectangle border.

enter image description here i saw many packages with circular border and using drawarc method in custom painter. How to draw roundrectangle border. I tried to customize code of a circular progress timer. but i am stuck on the round rectangle shape ANy packages also appreciated.

This is my code:

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

class CountDownTimer extends StatefulWidget {
  @override
  _CountDownTimerState createState() => _CountDownTimerState();
}

class _CountDownTimerState extends State<CountDownTimer>
    with TickerProviderStateMixin {
  late AnimationController controller;

  String get timerString {
    var durationValue = controller.duration! * controller.value;
    return '${(durationValue.inSeconds % 60).toString().padLeft(2, '0')}';
  }

  @override
  void initState() {
    super.initState();
    controller = AnimationController(
      vsync: this,
      duration: Duration(seconds: 60),
    );
    if (controller.isAnimating) {
      controller.stop();
    } else {
      controller.reverse(
          from: controller.value == 0.0 ? 1.0 : controller.value);
    }
  }

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

  @override
  Widget build(BuildContext context) {
    return AnimatedBuilder(
        animation: controller,
        builder: (context, child) {
          return Stack(
            alignment: Alignment.center,
            children: <Widget>[
              Container(
                height: 260,
                width: 260,
                decoration: BoxDecoration(
                    borderRadius: BorderRadius.circular(10),
                    color: Colors.red,
                    border: Border.all(width: 4, color: Colors.grey.shade400)),
                padding: EdgeInsets.all(8.0),
                child: Column(
                  mainAxisAlignment: MainAxisAlignment.spaceBetween,
                  children: <Widget>[
                    Expanded(
                      child: Align(
                        alignment: FractionalOffset.center,
                        child: AspectRatio(
                          aspectRatio: 1.0,
                          child: Stack(
                            children: <Widget>[
                              Positioned.fill(
                                child: CustomPaint(
                                    painter: CustomTimerPainter(
                                  animation: controller,
                                  backgroundColor: Colors.yellow,
                                  color: Colors.white,
                                )),
                              ),
                              Align(
                                alignment: FractionalOffset.center,
                                child: Column(
                                  mainAxisAlignment:
                                      MainAxisAlignment.spaceEvenly,
                                  crossAxisAlignment: CrossAxisAlignment.center,
                                  children: <Widget>[
                                    Text(
                                      timerString,
                                      style: TextStyle(
                                          fontSize: 15.0,
                                          fontWeight: FontWeight.w600),
                                    ),
                                  ],
                                ),
                              ),
                            ],
                          ),
                        ),
                      ),
                    ),
                  ],
                ),
              ),
            ],
          );
        });
  }
}

class CustomTimerPainter extends CustomPainter {
  CustomTimerPainter({
    required this.animation,
    required this.backgroundColor,
    required this.color,
  }) : super(repaint: animation);

  final Animation<double> animation;
  final Color backgroundColor, color;

  @override
  void paint(Canvas canvas, Size size) {
    var paint = Paint()
      ..color = backgroundColor
      ..strokeWidth = 15.0
      ..strokeCap = StrokeCap.butt
      ..style = PaintingStyle.stroke;

    var progress = animation.value;
    var path = Path();

    if (progress == 100) paint.color = Colors.green;
    canvas.drawArc(
        Offset.zero & size, math.pi * 1.5, progress * 6, false, paint);
  }

  @override
  bool shouldRepaint(CustomTimerPainter old) {
    return animation.value != old.animation.value ||
        color != old.color ||
        backgroundColor != old.backgroundColor;
  }
}
Asbah Riyas
  • 917
  • 1
  • 12
  • 28
  • 1
    check this [post](https://stackoverflow.com/questions/67336319/create-custom-circular-progress-indicator-in-flutter-with-custom-stroke-cap/67339219#67339219) it uses a somewhat similar approach to implement custom indicators (progress, timers, etc...) – Younss AIT MOU Jun 16 '21 at 11:02
  • Using draw arc i tried drawing circles... but i need round rectangle like shape(given in above image) – Asbah Riyas Jun 16 '21 at 11:07
  • just use `canvas.drawRRect()`instead and you're good to go – Younss AIT MOU Jun 16 '21 at 11:11
  • drawArc(Rect rect, double startAngle, double sweepAngle, bool useCenter, Paint paint), and drawRRect(RRect rrect, Paint paint) both have different arguments to pass – Asbah Riyas Jun 16 '21 at 11:14
  • check `PathMetric` class – pskink Jun 16 '21 at 12:54
  • 1
    [My post as example solution to your question](https://stackoverflow.com/questions/65011661/sqaure-progress-bar-with-corner-radius/70109785#70109785) I can't write in comment, forgive me :) – Szymon Nov 25 '21 at 11:15

0 Answers0