미팅 시간 제한 앱(데스크탑)
미팅 시간 타이머 앱. 압축 풀어서 exe파일 실행.
바이러스 없음. 소스코드가 간단하므로 확인할 수 있음.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
import 'dart:async';
import 'package:flutter/material.dart';
import 'dart:math';
void main() {
runApp(MyApp());
}
class MyApp extends StatelessWidget {
@override
Widget build(BuildContext context) {
return MaterialApp(
home: TimerHomePage(),
);
}
}
class TimerHomePage extends StatefulWidget {
@override
_TimerHomePageState createState() => _TimerHomePageState();
}
class _TimerHomePageState extends State {
final TextEditingController _hourController = TextEditingController(text: '00');
final TextEditingController _minuteController = TextEditingController(text: '00');
final TextEditingController _secondController = TextEditingController(text: '00');
double _progress = 0; // 타이머 진행률 (0.0에서 1.0까지)
Timer? _timer;
int _totalTime = 0; // 총 시간(초 단위)
// 타이머의 경과 시간과 남은 시간을 포맷팅하여 반환하는 함수
String formatDuration(int seconds) {
final int hours = seconds ~/ 3600;
final int minutes = (seconds % 3600) ~/ 60;
final int remainingSeconds = seconds % 60;
return '${hours.toString().padLeft(2, '0')}:${minutes.toString().padLeft(2, '0')}:${remainingSeconds.toString().padLeft(2, '0')}';
}
// _startTimer 함수 내에서 경과된 시간과 남은 시간을 계산하고 업데이트하는 부분
void _startTimer() {
int elapsedTime = 0;
_totalTime = (int.tryParse(_hourController.text) ?? 0) * 3600 +
(int.tryParse(_minuteController.text) ?? 0) * 60 +
(int.tryParse(_secondController.text) ?? 0);
_timer?.cancel(); // 기존 타이머가 있다면 취소
_timer = Timer.periodic(Duration(seconds: 1), (timer) {
setState(() {
elapsedTime++;
_progress = elapsedTime / _totalTime;
if (_progress >= 1) {
_timer?.cancel();
_showTimeUpDialog();
_progress = 0; // 타이머 초기화
_totalTime = 0;
}
});
});
}
void _showTimeUpDialog() {
showDialog(
context: context,
builder: (context) {
return AlertDialog(
title: Text('회의 시간 종료'),
content: Text('설정한 회의 시간이 종료되었습니다.'),
actions: [
TextButton(
child: Text('확인'),
onPressed: () {
Navigator.of(context).pop(); // 다이얼로그 닫기
},
),
],
);
},
);
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
@override
Widget build(BuildContext context) {
return Scaffold(
body: Center(
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
children: [
CustomPaint(
painter: TimerPainter(progress: _progress),
child: Container(
width: 200,
height: 200,
alignment: Alignment.center,
child: _timer != null && _timer!.isActive
? Text("${formatDuration(((_totalTime * _progress).round()))} / ${formatDuration(_totalTime)}")
: Text("시간을 설정하세요"),
),
),
SizedBox(height: 20),
Row(
mainAxisAlignment: MainAxisAlignment.center,
children: [
Flexible(
child: TextField(
controller: _hourController,
decoration: InputDecoration(
labelText: '시간 (hh)',
),
keyboardType: TextInputType.number,
textAlign: TextAlign.center,
),
),
SizedBox(width: 10),
Flexible(
child: TextField(
controller: _minuteController,
decoration: InputDecoration(
labelText: '분 (mm)',
),
keyboardType: TextInputType.number,
textAlign: TextAlign.center,
),
),
SizedBox(width: 10),
Flexible(
child: TextField(
controller: _secondController,
decoration: InputDecoration(
labelText: '초 (ss)',
),
keyboardType: TextInputType.number,
textAlign: TextAlign.center,
),
),
],
),
SizedBox(height: 20),
ElevatedButton(
onPressed: _startTimer,
child: Text('시작'),
),
],
),
),
);
}
@override
void dispose() {
_timer?.cancel();
_hourController.dispose();
_minuteController.dispose();
_secondController.dispose();
super.dispose();
}
}
class TimerPainter extends CustomPainter {
final double progress;
TimerPainter({required this.progress});
@override
void paint(Canvas canvas, Size size) {
Paint paint = Paint()
..color = Colors.blue
..strokeWidth = 8
..strokeCap = StrokeCap.round
..style = PaintingStyle.stroke;
Offset center = Offset(size.width / 2, size.height / 2);
double radius = size.width / 2;
double angle = 2 * pi * progress;
canvas.drawArc(Rect.fromCircle(center: center, radius: radius), -pi / 2, angle, false, paint);
}
@override
bool shouldRepaint(covariant CustomPainter oldDelegate) {
return true;
}
}
이 기사는 저작권자의 CC BY 4.0 라이센스를 따릅니다.