简体   繁体   中英

List contacts with phone numbers

I'd like to fetch (in iOS using Objective-C) only the contacts that have a phone number, but how can I do that? I'm trying to form the predicate as in the code below, but obviously that doesn't work.

contacts = [contactStore unifiedContactsMatchingPredicate:[NSPredicate predicateWithFormat:@"phoneNumbers <> nil"] keysToFetch:KEYS error:nil];

So, what is the correct way of doing this? Thanks for any help!

#import <Contacts/Contacts.h>


 CNContactStore *store = [[CNContactStore alloc] init];
    [store requestAccessForEntityType:CNEntityTypeContacts completionHandler:^(BOOL granted, NSError * _Nullable error) {
        if (granted == YES) {
            //keys with fetching properties
            NSArray *keys = @[CNContactFamilyNameKey, CNContactGivenNameKey, CNContactPhoneNumbersKey, CNContactImageDataKey, CNContactEmailAddressesKey];
            CNContactFetchRequest *request = [[CNContactFetchRequest alloc] initWithKeysToFetch:keys];
            request.sortOrder = CNContactSortOrderGivenName;
            request.unifyResults = YES;
            NSError *error;

            __block NSString* email;

            BOOL success = [store enumerateContactsWithFetchRequest:request error:&error usingBlock:^(CNContact * __nonnull contact, BOOL * __nonnull stop)
                            {
                                if (error) {
                                    NSLog(@"error fetching contacts %@", error);
                                } else {
                                    NSString *fullName;
                                    NSString* phone;

                                    //                    for (CNContact *contact in cnContacts) {
                                    DeviceContact *aContact = [DeviceContact new];

                                    // copy data to my custom Contacts class.
                                    NSString *firstName = contact.givenName;
                                    NSString *lastName = contact.familyName;

                                    if (lastName == nil) {
                                        fullName=[NSString stringWithFormat:@"%@",firstName];
                                    }else if (firstName == nil){
                                        fullName=[NSString stringWithFormat:@"%@",lastName];
                                    }
                                    else{
                                        fullName=[NSString stringWithFormat:@"%@ %@",firstName,lastName];
                                    }

                                    if ([firstName trim].length > 0) {
                                        aContact.nameForSorting = firstName; // 141116
                                    }else if ([lastName trim].length>0 && aContact.nameForSorting.length<=0) {
                                        aContact.nameForSorting = lastName; // 141116
                                    }

                                    aContact.name = fullName;


                                    if (contact.phoneNumbers!=nil && [contact.phoneNumbers count]>0) {
                                        for (CNLabeledValue *label in contact.phoneNumbers) {
                                            phone =  [CommonUtils removeAllSpecialCharactersFromPhoneNumber:[label.value stringValue]];
                                            if ([phone length] > 0) {
                                                [aContact.phoneNumber addObject:phone];
                                            }
                                        }
                                    }

                                    ////Get all E-Mail addresses from contacts
                                    /// if ([CommonUtils checkIsNullObject:[contact emailAddresses]] && [[contact emailAddresses] count]>0) {
                                    for (CNLabeledValue *label in contact.emailAddresses) {
                                        email = label.value;
                                        if ([email length] > 0)
                                        {
                                            [aContact.email addObject:email];
                                        }
                                    }
                                    // }

                                    // 141116
                                    if ([aContact.name trim].length <= 0) {
                                        if (aContact.email.count>0) {
                                            aContact.name = [aContact.email objectAtIndex:0];
                                        }else if (aContact.phoneNumber.count>0){
                                            aContact.name = [aContact.phoneNumber objectAtIndex:0];
                                        }
                                    }
                                    if ([aContact.nameForSorting trim].length <= 0){
                                        if (aContact.email.count>0) {
                                            aContact.nameForSorting = [aContact.email objectAtIndex:0];
                                        }else if (aContact.phoneNumber.count>0){
                                            aContact.nameForSorting = [aContact.phoneNumber objectAtIndex:0];
                                        }
                                    }

                                    [self.arrAllContacts addObject:aContact];
                                }

                            }];

            if(success){

                dispatch_async(dispatch_get_main_queue(), ^{
                    [CommonUtils hideLoader];

                    completionhandler(self.arrAllContacts);
                });
            }
        }
        else
        {
           // [CommonUtils showAlertMessageWithMessage:@"fdfdggfsgfdgfd" withDelegate:self withCancelTitle:OKAY isOtherButton:NO withOtherButtonTitle:nil withTag:0];
            [CommonUtils hideLoader];

        }
    }];

use following method and import

#import <AddressBook/AddressBook.h>
#import <Contacts/Contacts.h> 


-(void)contactsDetailsFromPhoneContactBook{
    CNContactStore *store = [[CNContactStore alloc] init];
    [store requestAccessForEntityType:CNEntityTypeContacts completionHandler:^(BOOL granted, NSError * _Nullable error) {
        if (granted == YES) {
            //keys with fetching properties
            NSArray *keys = @[CNContactFamilyNameKey,CNContactGivenNameKey];
            NSString *containerId = store.defaultContainerIdentifier;
            NSPredicate *predicate = [CNContact predicateForContactsInContainerWithIdentifier:containerId];
            NSError *error;
            NSArray *cnContacts = [store unifiedContactsMatchingPredicate:predicate keysToFetch:keys error:&error];
            if (error) {
                NSLog(@"error fetching contacts %@", error);
            } else {
                NSString *fullName;
                NSString *firstName;
                NSString *lastName;
                for (CNContact *contact in cnContacts) {
                    // copy data to my custom Contacts class.
                    firstName = contact.givenName;
                    lastName = contact.familyName;
                    if (lastName == nil) {
                        fullName=[NSString stringWithFormat:@"%@",firstName];
                    }else if (firstName == nil){
                        fullName=[NSString stringWithFormat:@"%@",lastName];
                    }
                    else{
                        fullName=[NSString stringWithFormat:@"%@ %@",firstName,lastName];
                    }
                    [self.contactsArray addObject:fullName];

                    NSLog(@"working or not %@",self.contactsArray);
                }

            }
        }
    }];
}

Filtering out the contacts that don't have a phone number (or some other property) is not possible. In the docs we read:

CNContact Predicates

Predicates to match contacts. You can only use these predicates with CNContactStore and CNContactFetchRequest.

  • predicateForContactsMatchingName: Returns a predicate to find the contacts matching the specified name.
  • predicateForContactsWithIdentifiers: Returns a predicate to find the contacts matching the specified identifiers.
  • predicateForContactsInGroupWithIdentifier: Returns a predicate to find the contacts that are members in the specified group.
  • predicateForContactsInContainerWithIdentifier: Returns a predicate to find the contacts in the specified container.

And additionally:

Compound predicates are not supported.

So, the only way to do the filtering would be to omit adding to the result array the contacts with no phone numbers. That could be done, for example, in the block of the enumerateContactsWithFetchRequest .

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM