zp_cccd_scanner

Flutter plugin quét và nhận diện thẻ CCCD / Căn cước Việt Nam bằng camera native, hiệu ứng giống Zalo: khi phát hiện đúng thẻ trong khung, frame đóng băng và tia quét chạy từ trên xuống.

  • iOS: AVFoundation + Vision (nhận diện chữ, QR, PDF417)
  • Android: CameraX + ML Kit bundled (Text Recognition Latin, Barcode)
  • Toàn bộ xử lý trên máy, không gửi ảnh ra ngoài

Thẻ được hỗ trợ

Mẫu thẻ Mặt trước Mặt sau
CCCD mã vạch (2016–2021) ✅ ✅ (PDF417)
CCCD gắn chip (2021–06/2024) ✅ (QR) ✅ (MRZ)
Thẻ Căn cước (từ 07/2024) ✅ ✅ (QR + MRZ)

CMND (hết hiệu lực từ 01/01/2025), GPLX, hộ chiếu, thẻ ngân hàng, giấy chứng nhận căn cước... đều bị loại.

Chống nhận nhầm

Chỉ chấp nhận khi có bằng chứng mạnh, rồi xác nhận lại lần 2 trên chính frame đã đóng băng:

  • MRZ (mặt sau thẻ chip / Căn cước): IDVNM, kiểm tra đủ 5 check digit ICAO 9303 (gồm check digit riêng của số định danh 12 số).
  • PDF417 trải ngang mép trên + cụm chữ đặc trưng (mặt sau CCCD mã vạch).
  • Mặt trước: so khớp cả dòng tiêu đề, số định danh hợp lệ (mã tỉnh, thế kỷ, năm sinh) và khớp chéo với ngày sinh / giới tính in trên thẻ.
  • Thẻ phải nằm trọn trong khung: dò 4 cạnh thẻ trên ảnh xám của vùng khung (dùng chung cho iOS/Android). Không chụp khi có góc bị cắt, thẻ quá gần / quá xa, hoặc tỉ lệ không đúng thẻ ID-1; lúc đó hiện hướng dẫn "Đưa toàn bộ thẻ vào trong khung".
  • Cùng kết luận ở 2 frame liên tiếp trong 1.5 s.

Cài đặt

dependencies:
  zp_cccd_scanner: ^1.0.0
  • iOS ≥ 15.5. Thêm vào Info.plist:
    <key>NSCameraUsageDescription</key>
    <string>Cần dùng camera để quét thẻ CCCD</string>
    
  • Android minSdk 21, Activity phải là FlutterActivity / FlutterFragmentActivity.

Sử dụng

Mỗi CccdScannerView quét đúng một mặt. Luồng eKYC: chụp mặt trước rồi mặt sau, sau đó kiểm tra 2 mặt cùng một thẻ.

final front = await Navigator.push<CccdScanResult>(context, MaterialPageRoute(
  builder: (context) => Scaffold(
    body: CccdScannerView(
      side: CccdSide.front,
      onScanned: (r) async => Navigator.pop(context, r),
    ),
  ),
));

// ... quét mặt sau tương tự với side: CccdSide.back

switch (CccdPairing.check(front!, back!)) {
  case CccdPairStatus.match:
  case CccdPairStatus.sameTypeOnly:
    // OK
    break;
  default:
    // Hai mặt không cùng một thẻ
}

CccdScanResult gồm: type (mẫu thẻ), side, image (JPEG chứa trọn thẻ), corners (4 góc thẻ), cardRect, pairingKey (khóa nội bộ để ghép 2 mặt). Lib không trích xuất họ tên, ngày sinh...

Tùy biến giao diện: guideWidthFactor, guideAlignment, maskColor, idleColor, detectedColor, scanLineColor, scanDuration, hintBuilder, overlay. Bật showDebugOverlay để xem các dòng chữ / mã native đọc được, 4 cạnh thẻ dò được (khung cam) và lý do từ chối của frame gần nhất.

App demo

cd example
fvm flutter run

Có 3 lựa chọn: quét riêng mặt trước, quét riêng mặt sau, và luồng eKYC (trước → sau → kiểm tra cùng thẻ).

Libraries

zp_cccd_scanner