import 'dart:io';

import 'package:camera/camera.dart';
import 'package:get/get.dart';
import 'package:myhr_facescan/luxand_controller.dart';
import 'package:myhr_facescan/models/face_match.dart';
import 'package:myhr_facescan/models/face_template.dart';
import 'package:myhr_facescan/models/template.dart';
import 'package:myhr_facescan/utils/camera.dart';
import 'package:myhr_facescan/utils/throttler.dart';

class MatchTemplateController extends GetxController {
  MatchTemplateController({
    required String licenseKey,
    required void Function(bool, TemplateModel?) onFinish,
    required int imageStreamMilliSecond,
    required List<FaceTemplate> templates,
  })  : _imageStreamMilliSecond = imageStreamMilliSecond,
        _onFinish = onFinish,
        _licenseKey = licenseKey,
        _templates = templates {
    _throttler = Throttler(milliSeconds: _imageStreamMilliSecond);
    _luxand = Get.put(LuxandController(licenseKey: _licenseKey));
  }

  CameraController? camController;
  double previewScale = 0;
  late Throttler _throttler;
  int failFrame = 0;
  // StreamSubscription<int> _timer = null;

  final String _licenseKey;
  final void Function(bool, TemplateModel?) _onFinish;
  final int _imageStreamMilliSecond;
  final List<FaceTemplate> _templates;

  var isCameraReady = false.obs;
  var faceMatchs = <FaceMatch>[].obs;

  late LuxandController _luxand;

  @override
  void onInit() async {
    super.onInit();

    await _luxand.initialize();
    // await _luxand.setAvailableTemplate(_templates);
    await initCamera();

    camController!.initialize().then((_) {
      isCameraReady.value = true;
      previewScale = getCameraPreviewScale(camController!.value.aspectRatio);

      // Only open and close camera in iOS for low-tier device
      if (Platform.isIOS) {
        // _timer = Stream.periodic(const Duration(milliseconds: 500), (v) => v)
        //     .listen((count) async {
        //   _throttler.run(() async {
        //     controller.startImageStream((image) async {});

        //     Future.delayed(const Duration(milliseconds: 50), () async {
        //       await controller.stopImageStream();
        //     });
        //   });
        // });
      } else {
        camController!.startImageStream(_handleCameraAndroid);
      }
    });
  }

  initCamera() async {
    camController = await getCameraController();
  }

  @override
  void onClose() async {
    super.onClose();
    await _clearResource();
  }

  _clearResource() async {
    isCameraReady.value = false;
    await camController?.stopImageStream();
    await camController?.dispose();

    await _luxand.freeResource();
  }

  _handleCameraAndroid(CameraImage image) async {
    _throttler.run(() async {
      var data = await _luxand.detectFaceForMatch(image, _templates);

      faceMatchs.value = data;
    });
  }
}
