728x90
반응형
Flutter 앱에서 날짜와 시간을 선택할 때, 과거 날짜나 현재 시간보다 이전 시간을 제한해야 하는 경우가 종종 있습니다. 이번 블로그에서는 **Flutter의 CupertinoDatePicker**와 유효성 검사 로직을 활용해 이러한 요구사항을 처리하는 방법을 소개합니다.
요구사항
- 과거 날짜는 선택할 수 없다.
사용자가 현재 날짜 이전의 날짜를 선택하려고 하면 이를 제한해야 합니다. - 현재 시간 및 과거 시간은 선택할 수 없다.
동일한 날짜일 경우, 현재 시간보다 이전 시간을 선택하면 제한하도록 설정합니다. - 오늘 날짜와 현재 시간 이후는 선택 가능해야 한다.
오늘 날짜인 경우, 현재 시점에서 몇 분 뒤의 시간까지 정상적으로 선택되도록 구현해야 합니다. - 제한 위반 시 사용자 알림 제공.
잘못된 선택을 시도할 경우 사용자에게 이유를 알리는 알림(Toast)을 제공해야 합니다.
2. 날짜 선택 로직 구현
날짜 선택에는 CupertinoDatePicker를 활용합니다. 날짜를 선택하면, 현재 날짜보다 과거인지를 확인하는 유효성 검사 로직을 추가합니다.
Future<String?> _showCupertinoDatePicker() async {
DateTime selectedDate = DateTime.now();
await showModalBottomSheet(
context: context,
builder: (_) {
return SizedBox(
height: 300.h,
child: Column(
children: [
Expanded(
child: CupertinoDatePicker(
mode: CupertinoDatePickerMode.date,
minimumDate: DateTime.now(), // 과거 날짜 제한
maximumDate: DateTime(2100), // 최대 날짜 제한
initialDateTime: DateTime.now(),
onDateTimeChanged: (dateTime) {
selectedDate = dateTime; // 선택된 날짜 업데이트
},
),
),
SizedBox(
width: double.infinity,
height: 48.h,
child: CupertinoButton(
padding: EdgeInsets.zero,
color: Colors.blue,
child: Text("확인", style: TextStyle(color: Colors.white)),
onPressed: () {
Navigator.of(context).pop();
},
),
),
],
),
);
},
);
return "${selectedDate.year}.${selectedDate.month.toString().padLeft(2, '0')}.${selectedDate.day.toString().padLeft(2, '0')}";
}
핵심 포인트:
- minimumDate로 과거 날짜를 선택하지 못하도록 설정.
- 사용자가 현재 날짜를 선택하더라도 유효성 검사 로직에서 확인 가능.
3. 시간 선택 로직 구현
시간 선택은 CupertinoDatePicker의 CupertinoDatePickerMode.time 모드를 활용합니다. 동일한 날짜인 경우, 현재 시간보다 이전 시간을 선택하지 못하도록 유효성 검사를 추가합니다.
Future<String?> _showCupertinoTimePicker() async {
TimeOfDay selectedTime = TimeOfDay.now();
await showModalBottomSheet(
context: context,
builder: (_) {
return SizedBox(
height: 300.h,
child: Column(
children: [
Expanded(
child: CupertinoDatePicker(
mode: CupertinoDatePickerMode.time,
use24hFormat: true, // 24시간 형식
initialDateTime: DateTime.now(),
onDateTimeChanged: (dateTime) {
final now = DateTime.now();
if (dateTime.isBefore(now)) {
// 현재 시간 이전 선택 시 알림
_showToast("현재 시간 및 과거 시간은 선택할 수 없습니다.");
} else {
selectedTime = TimeOfDay.fromDateTime(dateTime);
}
},
),
),
SizedBox(
width: double.infinity,
height: 48.h,
child: CupertinoButton(
padding: EdgeInsets.zero,
color: Colors.blue,
child: Text("확인", style: TextStyle(color: Colors.white)),
onPressed: () {
Navigator.of(context).pop();
},
),
),
],
),
);
},
);
final hour = selectedTime.hour.toString().padLeft(2, '0');
final minute = selectedTime.minute.toString().padLeft(2, '0');
return "$hour:$minute";
}
핵심 포인트:
- dateTime.isBefore(now)를 통해 과거 시간 제한.
- 잘못된 선택을 시도할 경우 사용자에게 Toast로 알림 제공.
4. 유효성 검사 로직 통합
날짜와 시간을 선택한 뒤, 버튼을 눌렀을 때 최종 유효성 검사를 수행합니다.
void _onNextButtonPressed() {
final now = DateTime.now();
final selectedDateTime = DateTime.parse(selectedDate!.replaceAll('.', '-'));
final selectedTimeOfDay = TimeOfDay(
hour: int.parse(selectedTime!.split(':')[0]),
minute: int.parse(selectedTime!.split(':')[1]),
);
final currentTime = TimeOfDay(hour: now.hour, minute: now.minute);
if (selectedDateTime.isBefore(now) ||
(selectedDateTime.isAtSameMomentAs(now) &&
(selectedTimeOfDay.hour < currentTime.hour ||
(selectedTimeOfDay.hour == currentTime.hour &&
selectedTimeOfDay.minute <= currentTime.minute)))) {
_showToast("현재 시간 및 과거 시간은 선택할 수 없습니다.");
} else {
print('다음 단계 실행: 날짜=$selectedDate, 시간=$selectedTime');
}
}
핵심 포인트:
- 날짜 및 시간이 과거인지 확인.
- 오늘 날짜인 경우 시간까지 세부적으로 검증.
5. Toast 알림 제공
사용자 알림을 위해 간단한 Toast 메시지를 구현합니다.
void _showToast(String message) {
final snackBar = SnackBar(
content: Text(message, style: TextStyle(color: Colors.white)),
backgroundColor: Colors.red,
duration: Duration(seconds: 2),
);
ScaffoldMessenger.of(context).showSnackBar(snackBar);
}
마무리
Flutter에서 날짜와 시간 선택 시 유효성 검사를 구현하는 것은 UI/UX를 향상시키는 중요한 요소입니다. 이 블로그에서 제공한 코드는 기본적인 유효성 검사뿐 아니라, 사용자 친화적인 알림 처리까지 포함합니다.
이제 이 코드를 활용해 Flutter 앱의 사용자 경험을 한 단계 업그레이드해보세요! 😊
728x90
반응형
LIST
'Flutter' 카테고리의 다른 글
Flutter 면접 질문: "왜 클래스 기반 위젯을 사용해야 할까?" (2) | 2025.02.12 |
---|---|
Flutter에서 SizedBox.shrink()를 활용하여 빈 공간 추가하는 방법 (2) | 2025.02.07 |
Flutter에서 반응형 배너 UI와 애니메이션 구현 (2) | 2025.01.13 |
Flutter에서 갤러리 이미지 선택 UI: 간격과 레이아웃 최적화 (이미지 썸네일) (1) | 2025.01.07 |
이미지 접근 (Ios , Android) 권한 (0) | 2025.01.07 |