import 'dart:convert';
import 'dart:io';
import 'dart:math';

import 'package:cached_network_image/cached_network_image.dart';
import 'package:flutter/material.dart';
import 'package:flutter/services.dart';
import 'package:flutter_cache_manager/flutter_cache_manager.dart';
import 'package:flutter_easyloading/flutter_easyloading.dart';
import 'package:http/http.dart' as http;
import 'package:image_cropper/image_cropper.dart';
import 'package:image_gallery_saver/image_gallery_saver.dart';
import 'package:image_picker/image_picker.dart';
import 'package:mime/mime.dart';
import 'package:permission_handler/permission_handler.dart';

import '../network/NetworkConfig.dart';

class AppUtil {
  /// 默认为下载网络图片，如需下载资源图片，需要指定 [isAsset] 为 `true`。
  static Future<void> saveImage(String imageUrl, {bool isAsset = false}) async {
    try {
      if (imageUrl == null) throw '保存失败，图片不存在！';

      print(NetworkConfig.systemVersion);

      /// 权限检测
      PermissionStatus storageStatus;

      ///android13及以上版本 "storage" 已废除  图片 视频  音频权限需要分别申请
      if (int.parse(NetworkConfig.systemVersion) >= 13) {
        storageStatus = await Permission.photos.status;
      } else {
        storageStatus = await Permission.storage.status;
      }

      if (storageStatus != PermissionStatus.granted) {
        if (int.parse(NetworkConfig.systemVersion) >= 13) {
          storageStatus = await Permission.photos.request();
        } else {
          storageStatus = await Permission.storage.request();
        }
        if (storageStatus != PermissionStatus.granted) {
          throw '无法存储图片，请先授权！';
        }
      }

      /// 保存的图片数据
      Uint8List imageBytes;

      if (isAsset == true) {
        /// 保存资源图片
        ByteData bytes = await rootBundle.load(imageUrl);
        imageBytes = bytes.buffer.asUint8List();
      } else {
        Map<String, String> map = {};

        /// 保存网络图片
        CachedNetworkImage image = CachedNetworkImage(imageUrl: imageUrl);
        BaseCacheManager manager = image.cacheManager ?? DefaultCacheManager();
        Map<String, String> headers =
            image.httpHeaders != null ? image.httpHeaders! : map;
        File file = await manager.getSingleFile(
          image.imageUrl,
          headers: headers,
        );
        imageBytes = await file.readAsBytes();
      }

      /// 保存图片
      final result =
          await ImageGallerySaver.saveImage(imageBytes, quality: 100);

      if (result == null || result == '') throw '图片保存失败';

      EasyLoading.showToast("Successfully saved");
    } catch (e) {
      print(e.toString());
    }
  }

  ///保存Widget图片
  static Future<void> saveWidgetImage(ByteData bytes) async {
    try {
      if (bytes == null) throw '保存失败，图片不存在！';

      /// 权限检测
      PermissionStatus storageStatus;

      ///android13及以上版本 "storage" 已废除  图片 视频  音频权限需要分别申请
      if (int.parse(NetworkConfig.systemVersion) >= 13) {
        storageStatus = await Permission.photos.status;
      } else {
        storageStatus = await Permission.storage.status;
      }

      if (storageStatus != PermissionStatus.granted) {
        if (int.parse(NetworkConfig.systemVersion) >= 13) {
          storageStatus = await Permission.photos.request();
        } else {
          storageStatus = await Permission.storage.request();
        }

        if (storageStatus != PermissionStatus.granted) {
          throw '无法存储图片，请先授权！';
        }
      }

      Uint8List imageBytes = bytes.buffer.asUint8List();

      /// 保存图片
      final result =
          await ImageGallerySaver.saveImage(imageBytes, quality: 100);

      if (result == null || result == '') throw '图片保存失败';

      EasyLoading.showToast("Successfully saved");
    } catch (e) {
      print(e.toString());
    }
  }

  //获取图片
  static Future<XFile> getImages() async {
    final pkImage = await ImagePicker().pickImage(
      source: ImageSource.gallery,
    );
    return pkImage!;
  }

  //裁剪
  static cropImage(BuildContext context, String path, int index) async {
    double x = 1.0;
    double y = 1.0;
    switch (index) {
      case 0:
        x = 1.0;
        y = 1.0;
        break;
      case 1:
        x = 3.0;
        y = 4.0;
        break;
      case 2:
        x = 4.0;
        y = 3.0;
        break;
      case 3:
        x = 9.0;
        y = 16.0;
        break;
      case 4:
        x = 16.0;
        y = 9.0;
        break;
    }
    CroppedFile? croppedFile = await ImageCropper().cropImage(
      maxHeight: 100,
      sourcePath: path,
      // aspectRatioPresets: [
      //   CropAspectRatioPreset.square, //1:1
      // ],
      //aspectRatio: CropAspectRatio(ratioX: x, ratioY: y),
      uiSettings: [
        IOSUiSettings(
          title: 'Cropper',
          aspectRatioLockEnabled: true,
          resetAspectRatioEnabled: false,
        ),
        AndroidUiSettings(
          toolbarTitle: 'Cropper',
          toolbarColor: Color(0xFFBE6FDF),
          toolbarWidgetColor: Colors.white,
          activeControlsWidgetColor: Color(0xFFBE6FDF),
          initAspectRatio: CropAspectRatioPreset.square,
          lockAspectRatio: true,
        ),
        WebUiSettings(
            context: context,
            viewwMode: WebViewMode.mode_1,
            cropBoxMovable: false
            /*customDialogBuilder: (cropper, initCropper, crop, rotate, scale) {
            return CropperDialog(
              cropper: cropper,
              initCropper: initCropper,
              crop: crop,
              rotate: rotate,
              scale: scale,
            );
          },*/
            ),
      ],
    );
    return croppedFile;
  }

  //解析图片转base64
  static uploadImage(XFile pickedFile) async {
    var file = File(pickedFile.path);
    String? type = lookupMimeType(pickedFile.path); //读取格式
    Uint8List imageBytes = await file.readAsBytes();
    String base64 = base64Encode(imageBytes);
    return "data:$type;base64,$base64";
  }

  //解析图片转base64
  static uploadImage2(File pickedFile) async {
    String? type = lookupMimeType(pickedFile.path); //读取格式
    Uint8List imageBytes = await pickedFile.readAsBytes();
    String base64 = base64Encode(imageBytes);
    return "data:$type;base64,$base64";
  }

  // 获取文件大小
  static String getFileSizeString({int? bytes, int decimals = 0}) {
    if (bytes! <= 0) return "0 Bytes";
    const suffixes = [" Bytes", "KB", "MB", "GB", "TB"];
    var i = (log(bytes) / log(1024)).floor();
    return ((bytes / pow(1024, i)).toStringAsFixed(decimals)) + suffixes[i];
  }

  // 获取文件大小(mb)
  static double getFileSizeDouble({int? bytes, int decimals = 0}) {
    final kb = bytes! / 1024;
    final mb = kb / 1024;
    print("object===$mb");
    return mb;
  }

  ///网络图片转base64
  static Future<String?> networkImageToBase64(String imageUrl) async {
    http.Response response = await http.get(Uri.parse(imageUrl));
    final bytes = response.bodyBytes;
    print("bytes===$bytes");
    return bytes != null ? base64Encode(bytes) : null;
  }
}
