import 'dart:io';

import 'package:geolocator/geolocator.dart';
import 'package:google_maps_flutter/google_maps_flutter.dart';
import 'package:hmg_patient_app_new/core/app_state.dart';
import 'package:hmg_patient_app_new/core/cache_consts.dart';
import 'package:hmg_patient_app_new/core/utils/utils.dart';
import 'package:hmg_patient_app_new/services/navigation_service.dart';
import 'package:permission_handler/permission_handler.dart';

class LocationUtils {
  NavigationService navigationService;
  AppState appState;

  bool isShowConfirmDialog;
  bool isShowLocationTimeoutDialog;
  bool isHuawei;
  final GeolocatorPlatform _geolocatorPlatform = GeolocatorPlatform.instance;

  LocationUtils({
    required this.isShowConfirmDialog,
    required this.navigationService,
    required this.appState,
    this.isHuawei = false,
    this.isShowLocationTimeoutDialog = true,
  });

  void getCurrentLocation({Function(LatLng)? callBack}) async {
    Geolocator.isLocationServiceEnabled().then((value) async {
      if (value) {
        await Geolocator.checkPermission().then((permission) async {
          if (permission == LocationPermission.always || permission == LocationPermission.whileInUse) {
            Geolocator.getLastKnownPosition().then((value) {
              setLocation(value);
              if (callBack != null) callBack(LatLng(value?.latitude ?? 24.7101433, value?.longitude ?? 46.6757709));
            }).catchError((err) {
              if (isShowConfirmDialog && isShowLocationTimeoutDialog) {}
            });
          }

          if (permission == LocationPermission.denied || permission == LocationPermission.deniedForever) {
            if (Platform.isAndroid) {
              // Utils.showPermissionConsentDialog(context, TranslationBase.of(context).locationPermissionDialog, () async {
              final hasPermission = await _handlePermission();
              if (hasPermission) {
                // Geolocator.getCurrentPosition(locationSettings: LocationSettings(accuracy: LocationAccuracy.medium, timeLimit: Duration(seconds: 5))).then((value) {
                Geolocator.getLastKnownPosition().then((value) {
                  setLocation(value);
                  if (callBack != null) callBack(LatLng(value?.latitude ?? 24.7101433, value?.longitude ?? 46.6757709));
                });
              } else {
                // if (isShowConfirmDialog) showErrorLocationDialog(false, failureCallBack: () {});
              }
              // });
            } else {
              if (await Permission.location.request().isGranted) {
                getCurrentLocation(callBack: callBack);
              } else {
                setZeroLocation();
                if (isShowConfirmDialog) showErrorLocationDialog(false, failureCallBack: () {});
              }
            }
          }
        }).catchError((err) {});
      } else {
        if (isShowConfirmDialog) showErrorLocationDialog(false, failureCallBack: () {});
      }
    }).catchError((err) {});
  }

  Future<bool> checkIfGPSIsEnabled() async {
    return await Geolocator.isLocationServiceEnabled();
  }

  Future<bool> _handlePermission() async {
    bool serviceEnabled;
    LocationPermission permission;

    serviceEnabled = await _geolocatorPlatform.isLocationServiceEnabled();
    if (!serviceEnabled) {
      return false;
    }

    permission = await _geolocatorPlatform.checkPermission();
    if (permission == LocationPermission.denied) {
      permission = await _geolocatorPlatform.requestPermission();
      if (permission == LocationPermission.denied) {
        return false;
      }
    }

    if (permission == LocationPermission.deniedForever) {
      return false;
    }
    return true;
  }

  // showLocationTimeOutDialog({Function()? failureCallBack}) {
  //   ConfirmDialog dialog = new ConfirmDialog(
  //       context: context,
  //       confirmMessage: TranslationBase.of(context).locationTimeoutError,
  //       okText: TranslationBase.of(context).ok,
  //       cancelText: TranslationBase.of(context).cancel_nocaps,
  //       okFunction: () {
  //         ConfirmDialog.closeAlertDialog(context);
  //         Navigator.of(context).canPop();
  //         if (failureCallBack != null) {
  //           failureCallBack();
  //         }
  //       },
  //       cancelFunction: () {
  //         if (failureCallBack != null) {
  //           failureCallBack();
  //         }
  //       });
  //   return dialog.showAlertDialog(context);
  // }

  showErrorLocationDialog(bool isPermissionError, {Function()? failureCallBack}) {
    setLocation(null);
    // ConfirmDialog dialog = new ConfirmDialog(
    //     context: context,
    //     confirmMessage: TranslationBase.of(context).locationDialogMessage,
    //     okText: TranslationBase.of(context).confirm,
    //     cancelText: TranslationBase.of(context).cancel_nocaps,
    //     okFunction: () {
    //       ConfirmDialog.closeAlertDialog(context);
    //       if (isPermissionError)
    //         Geolocator.openAppSettings();
    //       else
    //         Geolocator.openLocationSettings();
    //       Navigator.of(context).canPop();
    //       if (failureCallBack != null) {
    //         failureCallBack();
    //       }
    //     },
    //     cancelFunction: () {
    //       if (failureCallBack != null) {
    //         failureCallBack();
    //       }
    //     });
    // return dialog.showAlertDialog(context);
  }

  void setLocation(Position? position) {
    Utils.saveNumFromPrefs(CacheConst.userLat, position?.latitude ?? 0.0);
    Utils.saveNumFromPrefs(CacheConst.userLong, position?.longitude ?? 0.0);

    appState.setUserLat = position?.latitude ?? 0.0;
    appState.setUserLong = position?.longitude ?? 0.0;

    // projectViewModel.setLatitudeLongitude(position?.latitude ?? 0.0, position?.longitude ?? 0.0);
  }

  void setZeroLocation() {
    Utils.saveNumFromPrefs(CacheConst.userLat, 0.0);
    Utils.saveNumFromPrefs(CacheConst.userLong, 0.0);

    appState.setUserLat = 0.0;
    appState.setUserLong = 0.0;
  }

  Future<bool> requestPermissions() async {
    var result = await [
      Permission.location,
    ].request();
    return (result[Permission.location]!.isGranted || result[Permission.locationAlways]!.isGranted);
  }
}
