import 'package:clean/base/base_controller.dart';
import 'package:clean/data/bean/photos_type.dart';
import 'package:clean/module/image_picker/image_picker_util.dart';
import 'package:clean/module/people_photo/photo_group.dart';
import 'package:clean/module/photo_preview/photo_preview_controller.dart';
import 'package:clean/utils/toast_util.dart';
import 'package:get/get.dart';
import 'package:wechat_assets_picker/wechat_assets_picker.dart';

class PhotoSelectedPreviewController extends BaseController {
  late PhotosType photosType;

  final RxList<PhotoGroup> photoGroups = <PhotoGroup>[].obs;
  final RxDouble selectedFilesSize = 0.0.obs;
  RxInt selectedFileCount = 0.obs;
  RxList<AssetEntity> selectedPhotos = <AssetEntity>[].obs;
  late final RxSet<String> selectedPhotosIds;

  PhotoPreviewController photoPreviewController =
      Get.find<PhotoPreviewController>();

  @override
  onInit() {
    super.onInit();
    _getArgs();

    loadPhotoSelectedPreview();
  }

  _getArgs() {
    photosType = parameters?['photosType'];
    selectedPhotosIds = parameters?['selectedIds'];
  }

  loadPhotoSelectedPreview() {
    photoGroups.clear();
    for (var assetsEntity in photoPreviewController.photoGroups) {
      if (selectedPhotosIds.contains(assetsEntity.id)) {
        selectedPhotos.add(assetsEntity);
      }
    }
    if (selectedPhotos.isNotEmpty) {
      photoGroups.add(PhotoGroup(
        isSelected: true,
        images: selectedPhotos,
      ));
    }

    updateSelectedFilesSize();

    selectedFileCount.value = selectedPhotosIds.length;
  }

  void restoreSelections() async {
    for (var group in photoGroups) {
      for (int i = 0; i < group.images.length; i++) {
        if (selectedPhotosIds.contains(group.images[i].id)) {
          group.selectedImages[i] = true;
        } else {
          group.selectedImages[i] = false;
        }
      }
      group.isSelected.value =
          group.selectedImages.every((selected) => selected);
    }
    updateSelectedFilesSize();
    selectedFileCount.value = selectedPhotosIds.length;
  }

  clickDelete() async {
    print('clickDelete');
    switch (photosType) {
      case PhotosType.peoplePhotos:
        ImagePickerUtil.selectedPeoplePhotosIds.assignAll(selectedPhotosIds);
        break;
      case PhotosType.screenshots:
        ImagePickerUtil.selectedScreenshotPhotosIds
            .assignAll(selectedPhotosIds);
        break;
      case PhotosType.similarPhotos:
        ImagePickerUtil.selectedSimilarPhotosIds.assignAll(selectedPhotosIds);
        break;
      case PhotosType.locationPhotos:
        ImagePickerUtil.selectedLocationPhotosIds.assignAll(selectedPhotosIds);
        break;
      case PhotosType.blurryPhotos:
        ImagePickerUtil.selectedBlurryPhotosIds.assignAll(selectedPhotosIds);
        break;
    }
    if (selectedPhotosIds.isNotEmpty) {
      final assetsToDelete = photoGroups
          .expand((group) => group.images
              .where((asset) => selectedPhotosIds.contains(asset.id)))
          .toList();

      final List<String> result = await PhotoManager.editor.deleteWithIds(
        assetsToDelete.map((e) => e.id).toList(),
      );

      //   比较result和selectedPhotosIds，如果result和selectedPhotosIds相等，说明删除成功，走下面的逻辑
      // 如果不相等，说明有删除失败的，走else逻辑
      if (result.length == selectedPhotosIds.length) {
        switch (photosType) {
          case PhotosType.peoplePhotos:
            ImagePickerUtil.updatePhotoGroupDate(
                photosType, ImagePickerUtil.selectedPeoplePhotosIds);

            break;
          case PhotosType.screenshots:
            ImagePickerUtil.updatePhotoGroupDate(
                photosType, ImagePickerUtil.selectedScreenshotPhotosIds);

            break;
          case PhotosType.similarPhotos:
            ImagePickerUtil.updatePhotoGroupDate(
                photosType, ImagePickerUtil.selectedSimilarPhotosIds);

            break;
          case PhotosType.locationPhotos:
            ImagePickerUtil.updatePhotoGroupDate(
                photosType, ImagePickerUtil.selectedLocationPhotosIds);

            break;
          case PhotosType.blurryPhotos:
            ImagePickerUtil.updatePhotoGroupDate(
                photosType, ImagePickerUtil.selectedBlurryPhotosIds);

            break;
        }

        photoGroups.removeWhere((element) => element.images
            .any((image) => selectedPhotosIds.contains(image.id)));
        photoGroups.removeWhere((element) => element.images.isEmpty);
        selectedPhotosIds.clear();

        restoreSelections();
      } else {
        // 删除失败
        ToastUtil.show("Delete failed");
      }
    }
  }

  void toggleGroupSelection(List<AssetEntity> images) {
    final group = getGroupByImages(images);
    final newValue = !group.isSelected.value;
    group.toggleSelectAll(newValue);

    for (var image in group.images) {
      _updateSelectedPhotosIds(image.id, newValue);
    }

    updateSelectedFilesSize();
    selectedFileCount.value = selectedPhotosIds.length;
  }

  Future<void> updateSelectedFilesSize() async {
    double totalSize = 0;
    for (var group in photoGroups) {
      for (int i = 0; i < group.images.length; i++) {
        if (group.selectedImages[i]) {
          final file = await group.images[i].file;
          if (file != null) {
            totalSize += file.lengthSync();
          }
        }
      }
    }
    selectedFilesSize.value = totalSize / 1024; // Convert to KB
  }

  void clickImage(List<AssetEntity> images, int imageIndex) {
    final group = getGroupByImages(images);
    final image = group.images[imageIndex];
  }

  void toggleImageSelection(List<AssetEntity> images, int imageIndex) {
    final group = getGroupByImages(images);
    final image = group.images[imageIndex];
    final selected = !group.selectedImages[imageIndex];

    group.selectedImages[imageIndex] = selected;
    _updateSelectedPhotosIds(image.id, selected);

    group.isSelected.value = group.selectedImages.every((selected) => selected);

    updateSelectedFilesSize();
    selectedFileCount.value = selectedPhotosIds.length;
  }

  PhotoGroup getGroupByImages(List<AssetEntity> images) {
    final imageIds = images.map((img) => img.id).toSet();
    return photoGroups.firstWhere(
        (group) => group.images.every((image) => imageIds.contains(image.id)));
  }

  void _updateSelectedPhotosIds(String photoId, bool isSelected) {
    if (isSelected) {
      selectedPhotosIds.add(photoId);
    } else {
      selectedPhotosIds.remove(photoId);
    }
  }
}
