iphoneios5abaddressbook

Is this the right way to delete a contact from the iPhone?


I am trying to delete a contact from the iPhone which I have created. I tried to find a good working example of deleting a contact, however didn't find one. Adding a contact seemed quite easy but deleting one seems hard. The following code does not work, but it seemed to be plausible:

ABAddressBookRef addressBook = ABAddressBookCreate();
ABRecordRef delete = ABPersonCreate();

ABRecordSetValue(delete, kABPersonFirstNameProperty, @"Max", nil);
ABRecordSetValue(delete, kABPersonLastNameProperty, @"Mustermann", nil); 

ABAddressBookRemoveRecord(addressBook, delete, &error);
ABAddressBookSave(addressBook, &error);

Could anyone help me out.

Thanks in advance for your help.

Max


Solution

  • The problem is that you're creating an ABRecord that isn't inside of the address book. What you have to do is search through an array of ABRedords from the ABAddressBook. I wrote how to do this for you:

    CFErrorRef error = nil;
    
    ABAddressBookRef addressBook = ABAddressBookCreate();
    __block ABRecordRef toDelete = ABPersonCreate();
    
    ABRecordSetValue(toDelete, kABPersonFirstNameProperty, @"Max", nil);
    ABRecordSetValue(toDelete, kABPersonLastNameProperty, @"Mustermann", nil);
    
    // Gets the array of everybody in the address book
    NSArray *peopleArray = (__bridge NSArray *) ABAddressBookCopyArrayOfAllPeople(addressBook);
    
    // Creates a test predicate to see if the ABRecord has the same name as toDelete
    BOOL (^predicate)(id obj, NSUInteger idx, BOOL *stop) = ^(id obj, NSUInteger idx, BOOL *stop) {
        ABRecordRef person = (__bridge ABRecordRef)obj;
        CFComparisonResult result =  ABPersonComparePeopleByName(person, delete, kABPersonSortByLastName);
        bool pass = (result == kCFCompareEqualTo);
        if (pass) {
            toDelete = person;
        }
        return (BOOL) pass;
    };
    
    int idx = [peopleArray indexOfObjectPassingTest:predicate];
    
    bool removed = ABAddressBookRemoveRecord(addressBook, toDelete, &error);
    bool saved = ABAddressBookSave(addressBook, &error);
    

    You can change how you want to compare ABRecord instances by changing the block code. All it's doing now is comparing the names of the contacts.

    A caveat with this code is that it will only delete one instance of the ABRecords whose name matches delete’s.