Flutter is a popular open-source UI software development toolkit created by Google. It allows developers to build beautiful and high-performance mobile, web, and desktop applications from a single codebase. In this tutorial, we will explore how to create an analog clock using Flutter, making use of the Flutter framework's powerful and flexible widgets.
Prerequisites
Before we dive into the tutorial, make sure you have the following:
- Flutter SDK installed on your machine. You can download it from the official Flutter website and follow the installation instructions for your operating system.
- A basic understanding of Flutter widgets and how to set up a Flutter project.
Example 1 Analog Clock Using CustomPainter
Step 1: Create a New Flutter Project
To get started, open your terminal or command prompt and create a new Flutter project using the following command:
flutter create analog_clock_flutter
This will create a new Flutter project named 'analog_clock_flutter' with the necessary project structure.
Step 2: Design the Analog Clock UI
Now, navigate to the 'lib' folder of your project and open the 'main.dart' file. We will create a custom widget for our analog clock, so remove the default 'MyApp' widget and replace it with the following code:
import 'dart:math'; import 'package:flutter/material.dart'; void main() => runApp(const MyApp()); class MyApp extends StatelessWidget { const MyApp({super.key}); @override Widget build(BuildContext context) { return MaterialApp( debugShowCheckedModeBanner: false, theme: ThemeData.dark(), home: const AnalogClock(), ); } } class AnalogClock extends StatefulWidget { const AnalogClock({super.key}); @override _AnalogClockState createState() => _AnalogClockState(); } class _AnalogClockState extends State<AnalogClock> { @override Widget build(BuildContext context) { return Scaffold( backgroundColor: Colors.black, appBar: AppBar( title: const Text('FlutterforGeeks'), ), body: Center( child: Column( children: [ const SizedBox( height: 30, ), const Text( 'Analog Clock', style: TextStyle(fontSize: 24), ), const SizedBox( height: 200, ), SizedBox( width: 200, height: 200, child: CustomPaint( painter: ClockPainter(), ), ), ], ), ), ); } }
Step 3: Implement the Analog Clock CustomPainter
In the 'ClockPainter' class, we will implement the custom painting for our analog clock. We will draw the clock face, hour, minute, and second hands. Update the 'paint' method in the 'ClockPainter' class with the following code:
class ClockPainter extends CustomPainter { @override void paint(Canvas canvas, Size size) { // Draw clock face final centerX = size.width / 2; final centerY = size.height / 2; final centerOffset = Offset(centerX, centerY); final radius = size.width / 2; final facePaint = Paint() ..color = Colors.white ..style = PaintingStyle.fill; canvas.drawCircle(centerOffset, radius, facePaint); // Draw hour hand final hourHandPaint = Paint() ..color = Colors.black ..style = PaintingStyle.stroke ..strokeWidth = 6; final hour = DateTime.now().hour; final hourRadians = -(hour * 30 - 90) * (pi / 180); final hourHandX = centerX + (radius - 40) * cos(hourRadians); final hourHandY = centerY + (radius - 40) * sin(hourRadians); final hourHandOffset = Offset(hourHandX, hourHandY); canvas.drawLine(centerOffset, hourHandOffset, hourHandPaint); // Draw minute hand final minuteHandPaint = Paint() ..color = Colors.black ..style = PaintingStyle.stroke ..strokeWidth = 4; final minute = DateTime.now().minute; final minuteRadians = -(minute * 6 - 90) * (pi / 180); final minuteHandX = centerX + (radius - 30) * cos(minuteRadians); final minuteHandY = centerY + (radius - 30) * sin(minuteRadians); final minuteHandOffset = Offset(minuteHandX, minuteHandY); canvas.drawLine(centerOffset, minuteHandOffset, minuteHandPaint); // Draw second hand final secondHandPaint = Paint() ..color = Colors.red ..style = PaintingStyle.stroke ..strokeWidth = 2; final second = DateTime.now().second; final secondRadians = -(second * 6 - 90) * (pi / 180); final secondHandX = centerX + (radius - 20) * cos(secondRadians); final secondHandY = centerY + (radius - 20) * sin(secondRadians); final secondHandOffset = Offset(secondHandX, secondHandY); canvas.drawLine(centerOffset, secondHandOffset, secondHandPaint); } @override bool shouldRepaint(CustomPainter oldDelegate) { return true; } }
Step 4: Run the App
Save your changes and run the app using the following command:
flutter run
You should now see a beautiful analog clock with moving hour, minute, and second hands!
Step 5: Complete Source Code
import 'dart:math'; import 'package:flutter/material.dart'; void main() => runApp(const MyApp()); class MyApp extends StatelessWidget { const MyApp({super.key}); @override Widget build(BuildContext context) { return MaterialApp( debugShowCheckedModeBanner: false, theme: ThemeData.dark(), home: const AnalogClock(), ); } } class AnalogClock extends StatefulWidget { const AnalogClock({super.key}); @override _AnalogClockState createState() => _AnalogClockState(); } class _AnalogClockState extends State<AnalogClock> { @override Widget build(BuildContext context) { return Scaffold( backgroundColor: Colors.black, appBar: AppBar( title: const Text('FlutterforGeeks'), ), body: Center( child: Column( children: [ const SizedBox( height: 30, ), const Text( 'Analog Clock', style: TextStyle(fontSize: 24), ), const SizedBox( height: 200, ), SizedBox( width: 200, height: 200, child: CustomPaint( painter: ClockPainter(), ), ), ], ), ), ); } } class ClockPainter extends CustomPainter { @override void paint(Canvas canvas, Size size) { // Draw clock face final centerX = size.width / 2; final centerY = size.height / 2; final centerOffset = Offset(centerX, centerY); final radius = size.width / 2; final facePaint = Paint() ..color = Colors.white ..style = PaintingStyle.fill; canvas.drawCircle(centerOffset, radius, facePaint); // Draw hour hand final hourHandPaint = Paint() ..color = Colors.black ..style = PaintingStyle.stroke ..strokeWidth = 6; final hour = DateTime.now().hour; final hourRadians = -(hour * 30 - 90) * (pi / 180); final hourHandX = centerX + (radius - 40) * cos(hourRadians); final hourHandY = centerY + (radius - 40) * sin(hourRadians); final hourHandOffset = Offset(hourHandX, hourHandY); canvas.drawLine(centerOffset, hourHandOffset, hourHandPaint); // Draw minute hand final minuteHandPaint = Paint() ..color = Colors.black ..style = PaintingStyle.stroke ..strokeWidth = 4; final minute = DateTime.now().minute; final minuteRadians = -(minute * 6 - 90) * (pi / 180); final minuteHandX = centerX + (radius - 30) * cos(minuteRadians); final minuteHandY = centerY + (radius - 30) * sin(minuteRadians); final minuteHandOffset = Offset(minuteHandX, minuteHandY); canvas.drawLine(centerOffset, minuteHandOffset, minuteHandPaint); // Draw second hand final secondHandPaint = Paint() ..color = Colors.red ..style = PaintingStyle.stroke ..strokeWidth = 2; final second = DateTime.now().second; final secondRadians = -(second * 6 - 90) * (pi / 180); final secondHandX = centerX + (radius - 20) * cos(secondRadians); final secondHandY = centerY + (radius - 20) * sin(secondRadians); final secondHandOffset = Offset(secondHandX, secondHandY); canvas.drawLine(centerOffset, secondHandOffset, secondHandPaint); } @override bool shouldRepaint(CustomPainter oldDelegate) { return true; } }
GitHub Repository - Find the complete code for each example in this tutorial on GitHub.
Example 2 Analog Clock Using analog_clock Plugin
Step 1: Create a New Flutter Project
To begin, open your terminal or command prompt and create a new Flutter project using the following command:
flutter create analog_clock_flutter
Navigate into the project directory:
cd analog_clock_flutter
Step 2: Add the analog_clock Plugin
Open the pubspec.yaml
file in your project, and under the dependencies
section, add the analog_clock
plugin:
dependencies: flutter: sdk: flutter analog_clock: ^1.0.0
Save the file and run the following command in your terminal to get the new plugin:
flutter pub get
Step 3: Design the Analog Clock UI
Now, open the main.dart
file located in the lib
folder. Replace the default code with the following:
import 'package:flutter/material.dart'; import 'package:analog_clock/analog_clock.dart'; void main() => runApp(MyApp()); class MyApp extends StatelessWidget { @override Widget build(BuildContext context) { return MaterialApp( home: Scaffold( appBar: AppBar( title: Text('Analog Clock'), ), body: Center( child: AnalogClock( decoration: BoxDecoration( border: Border.all(width: 3.0, color: Colors.black), color: Colors.black, shape: BoxShape.circle), // decoration width: 200.0, height: 200, isLive: true, hourHandColor: Colors.white, minuteHandColor: Colors.white, showSecondHand: true, numberColor: Colors.white, showNumbers: true, textScaleFactor: 1.5, showTicks: true, showDigitalClock: true, digitalClockColor: Colors.white, datetime: DateTime(2020, 8, 4, 9, 11, 0), ), ), ), ); } }
Step 4: Run the App
Save your changes and run the app using the following command:
flutter run
Voilà! You should now see a stunning analog clock ticking away on your screen.
Video Demo
Conclusion
In this tutorial, we have learned how to create an analog clock in Flutter using the CustomPainter class. We utilized Flutter's powerful drawing capabilities to design the clock face and hands. With this foundation, you can further customize and enhance the clock to fit your specific needs.
Remember that this is just one way to create an analog clock in Flutter, and there are many possibilities for customization and refinement. I encourage you to experiment further with Flutter's widgets and explore its vast ecosystem to build even more impressive and engaging user interfaces.
Happy coding!