본문 바로가기

카테고리 없음

[Flutter_개발] 상품 등록 페이지 최종

핵심 코드/개념 정리

1) Form과 검증

  • GlobalKey<FormState>로 폼 전체를 제어하고, TextFormField/FormField의 validator로 필드별 검증을 수행.
  • 제출 전 FocusScope.of(context).unfocus()로 키보드 내리고, formKey.currentState?.validate()로 일괄 검사.
final _formKey = GlobalKey<FormState>();
// ...
final valid = _formKey.currentState?.validate() ?? false;
if (!valid) return;

2) 커스텀 FormField로 이미지 필수 처리

  • 이미지 선택은 일반 위젯이기 때문에, **별도의 FormField<String?>**로 감싸 validator를 붙임.
  • GlobalKey<FormFieldState<String?>>를 사용해 다이얼로그에서 선택 시 didChange로 값 변화를 폼에 반영.
final _imageFieldKey = GlobalKey<FormFieldState<String?>>();
setState(() => _imageSelection = 'network');
_imageFieldKey.currentState?.didChange(_imageSelection);

3) 가격 입력 포맷팅과 숫자 검증

  • FilteringTextInputFormatter.digitsOnly로 숫자만 허용.
  • TextInputFormatter.withFunction에서 intl의 NumberFormat('#,###')로 1,000 단위 콤마를 실시간 적용.
  • validator에서는 숫자 외 문자를 제거 후 범위(100 ~ 10,000,000) 검사.
inputFormatters: [
  FilteringTextInputFormatter.digitsOnly,
  TextInputFormatter.withFunction((oldValue, newValue) {
    if (newValue.text.isEmpty) return newValue;
    final number = int.parse(newValue.text.replaceAll(',', ''));
    final formatted = NumberFormat('#,###').format(number);
    return TextEditingValue(
      text: formatted,
      selection: TextSelection.collapsed(offset: formatted.length),
    );
  }),
],

4) Uuid로 엔터티 ID 생성 + 결과 전달

  • uuid.v4()로 고유 ID 생성, Navigator.pop(context, product)로 상위에 결과 반환.
  • 완료 전 미리 결과 요약을 AlertDialog로 보여줘 피드백 제공.
final product = ProductEntity(
  id: const Uuid().v4(),
  name: _nameController.text.trim(),
  price: int.parse(_priceController.text.replaceAll(',', '')),
  description: _descController.text.trim(),
  imageUrl: imageUrl,
);
Navigator.pop(context, product);

5) 이미지 네트워크 로딩 UX

  • Image.network의 loadingBuilder로 로딩 인디케이터, errorBuilder로 에러 메세지 제공.
  • ClipRRect + Card로 라운드 처리 및 테두리 스타일 일관화.

예외처리/검증 포인트 정리

  • 이미지: 선택 안 하면 “이미지를 등록해 주세요.”
  • 상품명: 공백/빈 문자열 금지, 최대 30자 제한.
  • 가격: 비어있음/음수/숫자 아님/범위 외(100 미만, 10,000,000 초과) 모두 차단.
  • 설명: 공백/빈 문자열 금지, 최대 1000자 제한.

상태/네비게이션/리소스 관리

  • TextEditingController는 dispose()에서 모두 해제 → 메모리 누수 방지.
  • 다이얼로그 사용 시 Navigator.pop(ctx) vs Navigator.pop(context, product)로 레이어 구분 주의.
  • SingleChildScrollView + SafeArea + padding으로 작은 화면/키보드 환경에서도 레이아웃 깨지지 않게 처리.

UI 구성 체크리스트

  • FilledButton.icon으로 이미지 선택 CTA 명확화.
  • OutlineInputBorder와 maxLength로 입력 경계/가이드 제공.
  • suffixText: '원', keyboardType: TextInputType.number로 입력 의도 전달.
  • TextInputAction.next로 필드 간 포커스 이동 자연스럽게.

 

 

최종 정리 끝! 내일 발표 준비 잘하자!