You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

iOS添加联系人后Table View未自动更新,仅重启生效求助

iOS通讯录添加后TableView不自动更新的修复方案

核心问题分析

  1. 错误的实例引用:在saveContact类中,你创建了全新的ViewController实例let viewControllerobj = ViewController(),调用它的方法完全不会影响屏幕上正在显示的那个ViewController。
  2. 未刷新数据源:即使调用了funcContactRel,也只是刷新了旧的contacts数组,没有重新从系统通讯录拉取最新数据。

修复步骤及修改代码

1. 修改tableView4:设置弹出页面的代理

在弹出saveContact时,将当前ViewController设置为它的代理,确保后续能通知到正确的实例:

class tableView4: UITableViewCell{
    
    var contactReloadDelegate: contactReload?
    
    @IBOutlet weak var btnAddContact: UIButton!
    @IBAction func btnClick(_ sender: Any) {
        
        guard let vc = UIStoryboard.main?.instantiateViewController(withIdentifier: "saveContact") as? saveContact else { return }
        // 将父ViewController设置为代理
        if let parentVC = self.parentViewController as? contactReload {
            vc.delegate = parentVC
        }
        self.parentViewController?.navigationController?.present(vc, animated: true)
    }
}

2. 修改saveContact:使用代理通知刷新

移除新建ViewController的代码,通过代理通知原页面刷新:

import Foundation
import ContactsUI

protocol contactReload {
    func funcContactRel()
}

class saveContact: UIViewController{
    var saveData = false
    // 添加代理属性
    var delegate: contactReload?
   
    @IBOutlet weak var contactName: UITextField!
    @IBOutlet weak var contactPhone: UITextField!
    
    override func viewDidLoad() {
        super.viewDidLoad()
    }
    
    @IBAction func saveContact(_ sender: UIButton) {
        
        let store = CNContactStore()
        let contact = CNMutableContact()

        contact.givenName = contactName.text ?? ""
        
        guard let phoneText = contactPhone.text, !phoneText.isEmpty else {
            print("手机号不能为空")
            return
        }
        contact.phoneNumbers.append(CNLabeledValue(
            label: CNLabelPhoneNumberMobile,
            value: CNPhoneNumber(stringValue: phoneText)))

        let saveRequest = CNSaveRequest()
        saveRequest.add(contact, toContainerWithIdentifier: nil)
        
        do {
            try store.execute(saveRequest)
            self.saveData = true
            // 通知代理刷新数据
            delegate?.funcContactRel()
        } catch {
            print("保存联系人失败:\(error.localizedDescription)")
            self.saveData = false
        }
        
        self.dismiss(animated: true) {
            print("dismiss")
        }
    }
}

3. 修改ViewController:刷新时重新获取最新数据

更新funcContactRel方法,确保重新拉取系统通讯录的最新数据:

class ViewController: UITableViewController, contactReload{
    
    func funcContactRel() {
        // 重新获取最新联系人数据,方法内部会自动刷新TableView
        contactDisplay()
    }
    
    // ... 其余原有代码保持不变 ...
}

修复说明

  • 代理模式解决了实例引用错误的问题,确保通知的是当前显示的ViewController
  • contactDisplay()方法会重新请求系统通讯录权限(已授权则直接拉取),更新contacts数组后自动调用tableView.reloadData()
  • 新增了手机号非空判断,避免无效数据保存

内容的提问来源于stack exchange,提问作者Hitesh Takhtani

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.30 20:27:19