Skip to main content

sprintfacedetection 0.1.0 copy "sprintfacedetection: ^0.1.0" to clipboard
sprintfacedetection: ^0.1.0 copied to clipboard

Native face liveness detection and attendance photo capture for Android (ML Kit) and iOS (Apple Vision). Standalone package with zero location or mapping dependencies.

sprintfacedetection #

Fast, native face detection for Flutter applications powered by Google ML Kit (Android) and Apple Vision (iOS).

Features #

  • ⚡ High Performance Native Stream Analysis: Directly processes CameraImage video stream frames in Kotlin (Android) and Swift (iOS) with minimal bridge overhead.
  • 👤 Facial Attributes & Landmarks: Extracts head pose angles (Pitch, Yaw, Roll), eye openness (left/right), smile probability, and mouth openness.
  • 💡 Luminance Detection: Calculates real-time ambient lighting levels directly from image buffers.
  • 🖼️ File Face Detection: Analyzes static image files (detectFaceInImageFile) using native platform ML Kit / Vision algorithms.
  • 🔒 Privacy-First On-Device AI: Zero network calls, 100% on-device processing.

Installation #

Add sprintfacedetection to your pubspec.yaml:

dependencies:
  sprintfacedetection: ^0.1.0
  camera: ^0.12.1

Platform Setup #

Android (android/app/src/main/AndroidManifest.xml)

Add camera permissions:

<uses-permission android:name="android.permission.CAMERA" />
<uses-feature android:name="android.hardware.camera" />

iOS (ios/Runner/Info.plist)

Add camera usage description:

<key>NSCameraUsageDescription</key>
<string>Camera access is required for real-time face detection.</string>

Usage #

1. Real-Time Camera Stream Analysis #

import 'package:camera/camera.dart';
import 'package:flutter/material.dart';
import 'package:sprintfacedetection/sprintfacedetection.dart';

class LiveFaceDetectionExample extends StatefulWidget {
  const LiveFaceDetectionExample({super.key});

  @override
  State<LiveFaceDetectionExample> createState() => _LiveFaceDetectionExampleState();
}

class _LiveFaceDetectionExampleState extends State<LiveFaceDetectionExample> {
  final FaceDetectionService _service = FaceDetectionService();
  CameraController? _controller;
  CustomFace? _detectedFace;
  bool _isProcessing = false;

  @override
  void initState() {
    super.initState();
    _initCamera();
  }

  Future<void> _initCamera() async {
    final cameras = await availableCameras();
    if (cameras.isEmpty) return;

    final frontCam = cameras.firstWhere(
      (c) => c.lensDirection == CameraLensDirection.front,
      orElse: () => cameras.first,
    );

    _controller = CameraController(
      frontCam,
      ResolutionPreset.medium,
      enableAudio: false,
    );

    await _controller!.initialize();

    _controller!.startImageStream((CameraImage image) async {
      if (_isProcessing) return;
      _isProcessing = true;

      try {
        final CustomFace? face = await _service.analyse(image, frontCam);
        if (mounted) {
          setState(() => _detectedFace = face);
        }
      } finally {
        _isProcessing = false;
      }
    });
  }

  @override
  void dispose() {
    _controller?.dispose();
    super.dispose();
  }

  @override
  Widget build(BuildContext context) {
    if (_controller == null || !_controller!.value.isInitialized) {
      return const Center(child: CircularProgressIndicator());
    }

    return Column(
      children: [
        Expanded(child: CameraPreview(_controller!)),
        if (_detectedFace != null) ...[
          Text('Face Detected! ID: ${_detectedFace!.trackingId}'),
          Text('Pitch: ${_detectedFace!.headEulerAngleX?.toStringAsFixed(1)}°'),
          Text('Yaw: ${_detectedFace!.headEulerAngleY?.toStringAsFixed(1)}°'),
          Text('Left Eye Open: ${(_detectedFace!.leftEyeOpenProbability ?? 0) * 100}%'),
          Text('Smile Probability: ${(_detectedFace!.smilingProbability ?? 0) * 100}%'),
        ],
      ],
    );
  }
}

2. Detect Face in Static Image File #

import 'package:sprintfacedetection/sprintfacedetection.dart';

Future<void> analyzeImageFile(String filePath) async {
  final service = FaceDetectionService();
  final Rect? faceBoundingBox = await service.detectFaceInImageFile(filePath);

  if (faceBoundingBox != null) {
    print('Face detected at bounding box: $faceBoundingBox');
    print('Width: ${faceBoundingBox.width}, Height: ${faceBoundingBox.height}');
  } else {
    print('No face found in image file.');
  }
}

CustomFace Data Class #

When a face is detected in a stream, analyse() returns a CustomFace object containing:

Property Type Description
trackingId int? Unique face tracking ID assigned by native ML Kit / Vision detector
boundingBox Rect Bounding box rectangle of the detected face in image coordinates
headEulerAngleX double? Head pitch angle (tilt up/down) in degrees
headEulerAngleY double? Head yaw angle (turn left/right) in degrees
headEulerAngleZ double? Head roll angle (tilt side) in degrees
leftEyeOpenProbability double? Probability that the left eye is open ($0.0 \dots 1.0$)
rightEyeOpenProbability double? Probability that the right eye is open ($0.0 \dots 1.0$)
smilingProbability double? Probability that the face is smiling ($0.0 \dots 1.0$)
mouthOpenProbability double? Probability that the mouth is open ($0.0 \dots 1.0$)
luminance double? Average lighting level computed directly from frame buffer

Example Project #

A complete runnable example project is available in the example/ folder.

0
likes
150
points
54
downloads

Documentation

API reference

Publisher

unverified uploader

Weekly Downloads

Native face liveness detection and attendance photo capture for Android (ML Kit) and iOS (Apple Vision). Standalone package with zero location or mapping dependencies.

Homepage

License

MIT (license)

Dependencies

camera, flutter, permission_handler, plugin_platform_interface, vector_math

More

Packages that depend on sprintfacedetection

Packages that implement sprintfacedetection