iOS获取通讯录的方法

目录

前言

1.什么是CNContactStore

2.获取通讯录权限

1.配置plist文件

2.请求访问通讯录授权

3.通讯录访问权限的其它配置       

3.获取通讯录中的联系人

4.获取通讯录中的群组

5.操作联系人

1.增加联系人

2.更新联系人信息

3.删除联系人信息

6.监听通讯录变化

8.参考文章


前言

    iOS中通讯录的用法。

1.什么是CNContactStore

        CNContactStore类是iOS中的一个框架,用于访问和管理设备上的通讯录数据。它提供了一种统一的方式来获取、添加、更新和删除联系人和群组,以及监听通讯录数据的变化。在iOS开发中,CNContactStore类具有重要性,因为它允许应用程序与设备上的通讯录进行交互,从而实现诸如获取联系人信息、同步联系人数据、发送通讯录相关的通知等功能。通过CNContactStore类,开发人员可以轻松地构建与通讯录相关的功能,提高应用程序的用户体验和功能性。

2.获取通讯录权限

        因为手机通讯录信息数据敏感信息,因此我们需要请求用户的授权。在用户未授权我们的app访问通讯录权限之前,app无法请求通讯录信息。描述要简单、清晰,让用户有信心授权app访问。

        请求用户授权访问手机通讯录之前,我们按照下面的步骤配置app项目。

1.配置plist文件

        首先我们需要再项目的plist文件中添加NSContactsUsageDescription属性,这个key对应的值用来描述app要执行的操作以及我们为什么要请求用户授权访问通讯录。如果没有配置这个key,app请求通讯录的时候,程序会终止。

2.请求访问通讯录授权

        我们先看下通讯录权限状态的类型定义,通讯类权限状态是一个CNAuthorizationStatus类型的枚举,定义如下:

typedef NS_ENUM(NSInteger, CNAuthorizationStatus){

    CNAuthorizationStatusNotDetermined = 0,//用户未决定是否授权访问

    CNAuthorizationStatusRestricted,//授权受限制

    CNAuthorizationStatusDenied,//拒绝授权

    CNAuthorizationStatusAuthorized//已经授权

} NS_ENUM_AVAILABLE(10_11, 9_0);

        这里需要注意的是只有当通讯录授权状态为CNAuthorizationStatusNotDetermined的时候,系统才会向用户展示一个弹窗,让用户选择是否授权app访问通讯录权限。其它状态下,系统不会再展示让用户选择是否授权状态的弹窗。

        app调用requestAccessForEntityType:completionHandler类方法,返回当前通讯录的授权状态。demo如下:

- (void)requestContactAccess{
    // 检查授权状态
    CNAuthorizationStatus status = [CNContactStore authorizationStatusForEntityType:CNEntityTypeContacts];
    // 请求授权
    // 请求授权
    if (status == CNAuthorizationStatusNotDetermined) {
        CNContactStore *store = [[CNContactStore alloc] init];
        [store requestAccessForEntityType:CNEntityTypeContacts completionHandler:^(BOOL granted, NSError * _Nullable error) {
            if (granted) {
                // 用户授予了授权,可以继续访问通讯录数据
                NSLog(@"用户已授权访问通讯录");
            } else {
                // 用户拒绝了授权,需要适当地处理这种情况
                NSLog(@"用户拒绝了访问通讯录的授权请求");
            }
        }];
    } else if (status == CNAuthorizationStatusDenied || status == CNAuthorizationStatusRestricted) {
        // 用户已经拒绝了授权或者授权受限,需要适当地处理这种情况
        NSLog(@"用户拒绝了访问通讯录的授权请求");
    } else {
        // 用户已经授予了授权,可以继续访问通讯录数据
        NSLog(@"用户已授权访问通讯录");
    }
}

3.通讯录访问权限的其它配置       

        如果我们需要再iOS13以及之后的版本读写联系人字段的时候,需要添加权限到app,得到apple的许可才能时候,在未得到Apple许可之前,是无法分发app的。具体的配置看这里。

        文档很详细,因为暂时没有发布app的需求,这个就不详细描述了。

3.获取通讯录中的联系人

        获取通讯录我们可以使用CNContactStore类,CNContactStore类是iOS中用于访问和操作通讯录数据的主要接口之一。它提供了一组方法来执行各种通讯录操作,包括读取、写入、更新和删除联系人、群组等。

        获取通讯录中的联系人信息的时候,我们需要使用CNContactFetchRequest创建通讯录请求。使用步骤如下:

        1.实例化CNContactStore对象,

    CNContactStore *store = [[CNContactStore alloc] init];

        2.实例化CNContactFetchRequest对象

CNContactFetchRequest *request = [[CNContactFetchRequest alloc] initWithKeysToFetch:@[CNContactGivenNameKey, CNContactFamilyNameKey, CNContactPhoneNumbersKey]];

        3.发起通讯录信息请求,完整代码如下:

- (void)fetchAllContactsInfor {
    CNContactStore *store = [[CNContactStore alloc] init];
    CNContactFetchRequest *request = [[CNContactFetchRequest alloc] initWithKeysToFetch:@[CNContactGivenNameKey, CNContactFamilyNameKey, CNContactPhoneNumbersKey, CNContactImageDataKey, CNContactPostalAddressesKey]];
    [store enumerateContactsWithFetchRequest:request error:nil usingBlock:^(CNContact * _Nonnull contact, BOOL * _Nonnull stop) {
        //后续操作
    }];
}

        这里需要注意的是通讯录请求是个异步耗时操作,建议使用异步多线程去处理。

4.获取通讯录中的群组

        我们使用 CNContactStore 类的 groupsMatchingPredicate:error: 方法来获取通讯录中的所有群组。该方法返回符合指定条件的通讯录群组数组。下面是一个获取通讯录群组的示例代码:

- (void)fetchAllGroupsCompletion:(void (^)(NSArray<CNGroup *> * _Nullable groups, NSError * _Nullable error))completion {
    CNContactStore *store = [[CNContactStore alloc] init];
    [store requestAccessForEntityType:CNEntityTypeContacts completionHandler:^(BOOL granted, NSError * _Nullable error) {
        if (!granted) {
            NSError *accessError = [NSError errorWithDomain:@"com.yourdomain.ContactManager" code:1 userInfo:@{NSLocalizedDescriptionKey: @"Access to contacts not granted"}];
            if (completion) {
                completion(nil, accessError);
            }
            return;
        }
        
        NSError *fetchError = nil;
        NSArray<CNGroup *> *groups = [store groupsMatchingPredicate:nil error:&fetchError];
        if (fetchError) {
            if (completion) {
                completion(nil, fetchError);
            }
        } else {
            if (completion) {
                completion(groups, nil);
            }
        }
    }];
}

5.操作联系人

1.增加联系人

        要在iOS中增加一个联系人信息,可以使用 CNMutableContact 类来创建一个可变的联系人对象,然后通过 CNContactStore 类的 executeSaveRequest:error: 方法将其保存到通讯录中。以下是一个示例代码:

- (void)addContactWithName:(NSString *)name phoneNumber:(NSString *)phoneNumber {
    // 创建一个可变的联系人对象
    CNMutableContact *contact = [[CNMutableContact alloc] init];
    
    // 设置联系人的姓名
    contact.givenName = name;
    
    // 创建一个电话号码对象,并添加到联系人的电话号码数组中
    CNLabeledValue *phoneNumberValue = [CNLabeledValue labeledValueWithLabel:CNLabelPhoneNumberMobile value:[CNPhoneNumber phoneNumberWithStringValue:phoneNumber]];
    contact.phoneNumbers = @[phoneNumberValue];
    
    // 创建联系人存储请求
    CNSaveRequest *saveRequest = [[CNSaveRequest alloc] init];
    [saveRequest addContact:contact toContainerWithIdentifier:nil]; // 使用默认的通讯录容器
    
    // 获取联系人存储对象
    CNContactStore *store = [[CNContactStore alloc] init];
    
    // 将联系人存储请求提交给通讯录
    NSError *error = nil;
    if (![store executeSaveRequest:saveRequest error:&error]) {
        NSLog(@"Error adding contact: %@", error.localizedDescription);
    } else {
        NSLog(@"Contact added successfully!");
    }
}

2.更新联系人信息

        要在iOS中更新联系人信息,可以使用 CNMutableContact 类创建一个可变的联系人对象,并将其修改后保存到通讯录中。以下是一个示例代码:

- (void)updateContactWithIdentifier:(NSString *)identifier withName:(NSString *)name phoneNumber:(NSString *)phoneNumber {
    // 获取联系人对象
    CNContactStore *store = [[CNContactStore alloc] init];
    NSError *error = nil;
    CNContact *contact = [store unifiedContactWithIdentifier:identifier keysToFetch:@[CNContactGivenNameKey, CNContactPhoneNumbersKey] error:&error];
    if (error) {
        NSLog(@"Error fetching contact: %@", error.localizedDescription);
        return;
    }
    
    // 创建一个可变的联系人对象,并复制原始联系人的属性
    CNMutableContact *mutableContact = [contact mutableCopy];
    
    // 更新联系人的姓名和电话号码
    mutableContact.givenName = name;
    CNPhoneNumber *newPhoneNumber = [CNPhoneNumber phoneNumberWithStringValue:phoneNumber];
    CNLabeledValue *phoneNumberValue = [CNLabeledValue labeledValueWithLabel:CNLabelPhoneNumberMobile value:newPhoneNumber];
    mutableContact.phoneNumbers = @[phoneNumberValue];
    
    // 创建联系人存储请求
    CNSaveRequest *saveRequest = [[CNSaveRequest alloc] init];
    [saveRequest updateContact:mutableContact];
    
    // 提交联系人存储请求给通讯录
    if (![store executeSaveRequest:saveRequest error:&error]) {
        NSLog(@"Error updating contact: %@", error.localizedDescription);
    } else {
        NSLog(@"Contact updated successfully!");
    }
}

        在这个示例中,我们首先通过联系人的唯一标识符获取到原始的 CNContact 对象。然后,我们创建一个可变的 CNMutableContact 对象,并使用原始联系人的属性对其进行初始化。接下来,我们更新了联系人的姓名和电话号码。最后,我们创建了一个 CNSaveRequest 对象,并通过 updateContact: 方法将修改后的联系人对象添加到保存请求中。最终,我们使用 CNContactStore 对象的 executeSaveRequest:error: 方法来执行保存请求。

3.删除联系人信息

        要在iOS中删除联系人信息,可以使用 CNMutableContact 类创建一个可变的联系人对象,并将其标记为已删除,然后保存到通讯录中。以下是一个示例代码:

- (void)deleteContactWithIdentifier:(NSString *)identifier {
    // 获取联系人对象
    CNContactStore *store = [[CNContactStore alloc] init];
    NSError *error = nil;
    CNContact *contact = [store unifiedContactWithIdentifier:identifier keysToFetch:@[] error:&error];
    if (error) {
        NSLog(@"Error fetching contact: %@", error.localizedDescription);
        return;
    }
    
    // 创建一个可变的联系人对象,并将其标记为已删除
    CNMutableContact *mutableContact = [contact mutableCopy];
    mutableContact.contactType = CNContactTypePerson;
    
    // 创建联系人存储请求
    CNSaveRequest *saveRequest = [[CNSaveRequest alloc] init];
    [saveRequest deleteContact:mutableContact];
    
    // 提交联系人存储请求给通讯录
    if (![store executeSaveRequest:saveRequest error:&error]) {
        NSLog(@"Error deleting contact: %@", error.localizedDescription);
    } else {
        NSLog(@"Contact deleted successfully!");
    }
}

        在这个示例中,我们首先通过联系人的唯一标识符获取到原始的 CNContact 对象。然后,我们创建一个可变的 CNMutableContact 对象,并使用原始联系人的属性对其进行初始化。接下来,我们将可变联系人对象的 contactType 属性设置为 CNContactTypePerson,这将将联系人标记为普通个人联系人。最后,我们创建了一个 CNSaveRequest 对象,并通过 deleteContact: 方法将标记为已删除的联系人对象添加到保存请求中。最终,我们使用 CNContactStore 对象的 executeSaveRequest:error: 方法来执行保存请求。

6.监听通讯录变化

        要在iOS应用中监听通讯录的变化,可以使用 CNContactStoreDidChangeNotification 通知。

8.参考文章

1.Apple官方文档

2.权限配置

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mfbz.cn/a/584511.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

【软考高项】第十二章 项目质量管理

目录 12.1管理基础 12.1.1质量与项目质量 12.1.2质量管理 12.1.3质量管理标准体系 12.1.4管理新实践 12.2项目质量管理过程 12.2.1过程概述 12.2.2裁剪考虑因素 12.2.3敏捷与适应方法 12.3规划质量管理 12.3.1输入 12.3.2工具与技术 12.3.3输出 12.4管理质量 12…

最小K个数(力扣面试题17.14)

本文采用的是大堆排序求最小的K个值。需要有堆的数据结构基础哦。 代码展示&#xff1a; /*** Note: The returned array must be malloced, assume caller calls free().*/ void AdjustDown(int* parr,int n,int root)//向下调整 {int parentroot;int child parent*21;while…

opencv_23_高斯模糊

void ColorInvert::gaussian_blur(Mat& image) { Mat dst; GaussianBlur(image, dst, Size(0, 0), 15); // Size(2, 2), imshow("图像模糊2", dst); }

代码随想录算法训练营DAY42|C++动态规划Part4|0-1背包理论基础(一)、0-1背包理论基础之滚动数组(二)、416.分割等和子集

文章目录 0-1背包理论基础(一)前置知识01背包动态规划&#xff1a;01背包二维dp数组 CPP代码再论01背包的遍历顺序 0-1背包理论基础(二)一维dp数组如何初始化一维dp数组遍历顺序举例推导dp数组CPP代码 416.分割等和子集思路将题目抽象成0-1背包问题 CPP代码 0-1背包理论基础(一…

2013NOIP普及组真题 4. 车站分级

线上OJ&#xff1a; 一本通&#xff1a;http://ybt.ssoier.cn:8088/problem_show.php?pid1964 核心思想&#xff1a; 1、原文中提到 “如果这趟车次停靠了火车站 x&#xff0c;则始发站、终点站之间所有级别大于等于火车站 x 的都必须停靠”&#xff0c;如果设停靠站为A&…

ansible-playbook离线升级centos内核

目录 概述实践ansible目录结构关键代码执行效果 结束 概述 内核离线包官网下载地址如下&#xff1a; 地址 实践 ansible目录结构 如对 ansible 不熟悉&#xff0c;离线包下载有问题&#xff0c;请至此地址下载&#xff0c;按本文操作可直接使用。 相关文章链接如下 文章地…

如何在iPhone上恢复出厂设置后恢复数据

你不想让这种情况发生&#xff0c;但它确实发生了。您必须将iPhone恢复出厂设置。当您的 iPhone 上出现软件问题且无法修复时&#xff0c;可能会发生这种情况。相反&#xff0c;在更新期间&#xff0c;或者您的iPhone遇到问题时&#xff0c;iPhone上的数据不再存在。 不过不用…

goget配置多个golang 运行环境

一台主机安装多个golang 运行环境 本环境 windows10 为 基础 mac linux也可以按照此方法操作 背景 开发不同的运维工具会用到不同版本的golang&#xff0c;但是开发者不能一直进行重装来处理 &#xff0c;因此 需要一个工具进行golang版本的管理 go管理工具介绍 gvm (Go V…

android webview检测屏幕

1&#xff09;清单文件配置&#xff1a; 配置权限&#xff1a; <uses-permission android:name"android.permission.INTERNET" /> 注册activity&#xff1a; <activityandroid:name".TouchWebViewActivity"android:exported"true"&…

基于随机森林和Xgboost对肥胖风险的多类别预测

基于随机森林和Xgboost对肥胖风险的多类别预测 作者&#xff1a;i阿极 作者简介&#xff1a;数据分析领域优质创作者、多项比赛获奖者&#xff1a;博主个人首页 &#x1f60a;&#x1f60a;&#x1f60a;如果觉得文章不错或能帮助到你学习&#xff0c;可以点赞&#x1f44d;收藏…

学习【Mysql运维篇】这一篇就够了

运维篇 1. 日志1-1. 错误日志1-2. 二进制日志1-3. 查询日志1-4. 慢查询日志 2. 主从复制2-1. 概述2-2. 原理2-3. 搭建 3. 分库分表3-1. 介绍3-2. Mycat概述3-3. Mycat入门3-4. Mycat配置3-5. Mycat分片3-6. Mycat管理及监控 4. 读写分类 1. 日志 1-1. 错误日志 错误日志是MyS…

计算机服务器中了mkp勒索病毒怎么办,mkp勒索病毒解密数据恢复流程

网络技术的不断应用与发展&#xff0c;为企业的生产运营带来了极大便利&#xff0c;越来越多的企业依赖网络开展各项工作业务&#xff0c;网络也大大提升了企业的生产运营效率&#xff0c;但网络是一把双刃剑&#xff0c;在为企业提供便利的同时&#xff0c;也为企业的数据安全…

云里物里家电运输新模式:实时定位、智能监控、降本增效

随着电商行业的飞速发展&#xff0c;大家电作为大宗商品&#xff0c;其物流运输过程中面临的痛点日益凸显。如何确保大家电在运输过程中的安全、及时送达以及成本控制&#xff0c;成为了物流企业亟待解决的问题。云里物里自研的物流资产监控管理方案&#xff0c;有效解决了大家…

JAVA面试题分享--集合

常见的数据结构&#xff08;了解&#xff09; 常用的数据结构有&#xff1a;数组&#xff0c;栈&#xff0c;队列&#xff0c;链表&#xff0c;树&#xff0c;散列&#xff0c;堆&#xff0c;图等 数组是最常用的数据结构&#xff0c;数组的特点是长度固定&#xff0c;数组的大…

一、交换网络基础

目录 1.交换机的转发行为 2.数据帧的类型 3.ARP地址解析步骤 Hub&#xff1a;物理层设备 交换机&#xff1a;数据链路层设备 1.交换机的转发行为 泛洪&#xff08;Flooding&#xff09;&#xff08;有可能是单播帧&#xff08;未知单播帧&#xff09;&#xff0c;也有可能是…

10GMAC层设计系列-(1)10G Ethernet PCS/PMA

一、引言 对于10G以太网MAC层的实现&#xff0c;Xilinx提供了 3种IP核&#xff0c;分别是 10G Ethernet MAC、10G Ethernet PCS/PMA、10G Ethernet Subsystem。 10G Ethernet MAC只包含MAC层&#xff0c;外部需要提供一个PHY芯片进行数据对齐&#xff0c;10G Ethernet MAC与P…

Python 深度学习(二)

原文&#xff1a;zh.annas-archive.org/md5/98cfb0b9095f1cf64732abfaa40d7b3a 译者&#xff1a;飞龙 协议&#xff1a;CC BY-NC-SA 4.0 第五章&#xff1a;图像识别 视觉可以说是人类最重要的感官之一。我们依赖视觉来识别食物&#xff0c;逃离危险&#xff0c;认出朋友和家人…

Kompas.ai的可持续内容生态:绿色营销的新选择

在全球环境保护意识日益增强的今天&#xff0c;绿色营销已成为企业树立品牌形象、展示社会责任的重要手段。绿色营销不仅关注产品的环保特性&#xff0c;还包括企业的整体可持续发展战略和对环境的积极贡献。本文将讨论企业如何通过绿色营销树立品牌形象&#xff0c;介绍Kompas…

el-cascader 数据回显 checkbox没有被勾选

需求&#xff1a; 需要支持多选以及能搜索&#xff0c;并且 点击所有队伍最新版本这个功能按钮时&#xff0c;要将用户勾选的数据保存的前提下&#xff0c;将满足条件的数据也一并勾选。最后保存的数据 只需要子级的id&#xff0c;组成数组就行了&#xff0c;所以我这里有用到…

ITMS-90426: Invalid Swift Support

原文 Please correct the following issues and upload a new binary to App Store Connect. ITMS-90426: Invalid Swift Support - The SwiftSupport folder is missing. Rebuild your app using the current public (GM) version of Xcode and resubmit it. 解决方式 ITMS-…
最新文章