import 'package:clean/base/base_controller.dart'; import 'package:clean/data/repositories/user_repository.dart'; import 'package:clean/module/contact/contact_state.dart'; import 'package:clean/module/store/store_view.dart'; import 'package:clean/utils/toast_util.dart'; import 'package:flutter_contacts/contact.dart'; import 'package:flutter_contacts/flutter_contacts.dart'; import 'package:get/get_rx/src/rx_types/rx_types.dart'; import '../../../dialog/loading_dialog.dart'; class ContactDuplicateController extends BaseController { // 是否为编辑状态 RxBool isEdit = false.obs; // 是否全选 RxBool isAllSelected = false.obs; RxMap> contactsByPhoneNumber = >{}.obs; var contactCount = 0; // RxMap> contactsByPhoneNumber = >{}.obs; // 存储选中的联系人ID final RxSet selectedContacts = {}.obs; @override void onInit() { // TODO: implement onInit super.onInit(); loadDuplicateContacts(); } Future loadDuplicateContacts() async { Map> groupedContacts = {}; // 获取所有联系人 List contacts = await FlutterContacts.getContacts( withProperties: true, withPhoto: true, ); // 按名字的首字母排序 contacts .sort((a, b) => (a.displayName ?? '').compareTo(b.displayName ?? '')); for (var contact in contacts) { if (contact.phones.isNotEmpty) { for (var phone in contact.phones) { final phoneNumber = phone.number; if (phoneNumber.isNotEmpty) { if (!groupedContacts.containsKey(phoneNumber)) { groupedContacts[phoneNumber] = []; } groupedContacts[phoneNumber]!.add(contact); } } } } Map> tempContacts = {}; tempContacts.addAll(groupedContacts); for (var key in groupedContacts.keys) { if (groupedContacts[key]?.length == 1) { tempContacts.remove(key); } } contactsByPhoneNumber.value = tempContacts; contactCount = 0; for (var key in contactsByPhoneNumber.keys) { if (contactsByPhoneNumber[key] != null) { contactCount += contactsByPhoneNumber[key]!.length; } } } // 选择/取消选择联系人 void toggleSelectContact(String phoneNumber) { // final asset = ContactState.contactList.firstWhere((contact) => contact.id == selectContact.id); final contacts = contactsByPhoneNumber[phoneNumber]; if (contacts != null) { for (var contact in contacts) { if (selectedContacts.contains(contact.id)) { selectedContacts.remove(contact.id); } else { selectedContacts.add(contact.id); } } } // 更新全选状态 isAllSelected.value = selectedContacts.length == contactCount; } // 全选/取消全选 void toggleSelectAll() { if (isAllSelected.value) { selectedContacts.clear(); } else { for (var key in contactsByPhoneNumber.keys) { if (contactsByPhoneNumber[key] != null) { for (var contact in contactsByPhoneNumber[key]!) { selectedContacts.add(contact.id); } } } } isAllSelected.value = !isAllSelected.value; } // 退出编辑模式时清空选择 void exitEditMode() { isEdit.value = false; selectedContacts.clear(); isAllSelected.value = false; } Future mergeBtnClick(List contacts) async { if (!userRepository.isVip()) { StorePage.start(); return; } LoadingDialog.show(); Contact? contactWithMostInfo; int maxInfoCount = 0; for (var contact in contacts) { final infoCount = _countContactInfo(contact); if (infoCount > maxInfoCount) { maxInfoCount = infoCount; contactWithMostInfo = contact; } } for (var contact in contacts) { if (contact.id != contactWithMostInfo?.id) { await contact.delete(); } } Future.delayed(Duration(milliseconds: 300), () async { LoadingDialog.hide(); ToastUtil.show("Successful"); exitEditMode(); await loadDuplicateContacts(); }); } void deleteBtnClick() { // 获取要删除的资产 final contactToDelete = ContactState.contactList .where((contact) => selectedContacts.contains(contact.id)) .toList(); LoadingDialog.show(); for (var contact in contactToDelete) { contact.delete(); } Future.delayed(Duration(milliseconds: 300), () { ToastUtil.show("Successful"); exitEditMode(); ContactState.loadContacts(); }); } // 统计联系人的信息数量 int _countContactInfo(Contact contact) { int count = 0; // 统计姓名 if (contact.name.first.isNotEmpty || contact.name.last.isNotEmpty) { count++; } // 统计电话号码 if (contact.phones.isNotEmpty) { count += contact.phones.length; } // 统计电子邮件 if (contact.emails.isNotEmpty) { count += contact.emails.length; } // 统计地址 if (contact.addresses.isNotEmpty) { count += contact.addresses.length; } if (contact.events.isNotEmpty) { count += contact.events.length; } if (contact.notes.isNotEmpty) { count += contact.notes.length; } if (contact.socialMedias.isNotEmpty) { count += contact.socialMedias.length; } if (contact.websites.isNotEmpty) { count += contact.websites.length; } if (contact.organizations.isNotEmpty) { count += contact.organizations.length; } // 统计图片 if (contact.photo != null) { if (contact.photo!.isNotEmpty) { count++; } } return count; } }