Reputation: 77
I am trying to get selected mobile phone number with
ABMultiValueRef phones = ABRecordCopyValue(person, property);
CFStringRef phoneNumber = ABMultiValueCopyValueAtIndex(phones, identifier);
I have a contact with several mobile phones (all labeled 'mobile'). When I select the first one, phoneNumber gives me the first one, but if I select any consecutive one, phoneNumber gives me the previous number:
Contact: Jay Jaymes mobile +1111111111 mobile +2222222222 mobile +3333333333
Tap first one, phoneNumber
= +1111111111
Tap second one, phoneNumber
= +1111111111
Tap third one, phoneNumber
= +2222222222
Upvotes: 4
Views: 1731
Reputation: 4671
This is code I use. And It will give correct phone number only
- (BOOL)peoplePickerNavigationController:(ABPeoplePickerNavigationController *)peoplePicker shouldContinueAfterSelectingPerson:(ABRecordRef)person property:(ABPropertyID)property identifier:(ABMultiValueIdentifier)identifier {
if (property == kABPersonPhoneProperty) {
ABMultiValueRef phoneProperty = ABRecordCopyValue(person,property);
CFIndex peopleIndex = ABMultiValueGetIndexForIdentifier(property, identifier);
NSString *phone = (__bridge_transfer NSString*)ABMultiValueCopyValueAtIndex(phoneProperty, peopleIndex);
[self dismissModalViewControllerAnimated:YES];
}
return NO;
}
Upvotes: 4
Reputation: 437552
You should not be using the identifier
as the index within ABMultiValueCopyValueAtIndex
. You should call ABMultiValueGetIndexForIdentifier
to convert the ABMultiValueIdentifier
identifier into a CFIndex
index:
ABMultiValueRef phones = ABRecordCopyValue(person, property);
CFIndex index = ABMultiValueGetIndexForIdentifier(phones, identifier);
NSString *phoneNumber = CFBridgingRelease(ABMultiValueCopyValueAtIndex(phones, index));
CFRelease(phones);
Generally, the ABMultiValueIdentifier
values match the CFIndex
values retrieved by ABMultiValueGetIndexForIdentifier
, but if a contact was edited (specifically if one of the earlier phone numbers was deleted), using the ABMultiValueIdentifier
in ABMultiValueCopyValueAtIndex
will return the wrong record.
Upvotes: 0
Reputation: 77
Ended up implementing it this way:
- (BOOL)peoplePickerNavigationController:(ABPeoplePickerNavigationController *)peoplePicker shouldContinueAfterSelectingPerson:(ABRecordRef)person property:(ABPropertyID)property identifier:(ABMultiValueIdentifier)identifier
{
if (property == kABPersonPhoneProperty)
{
ABMultiValueRef phones = ABRecordCopyValue(person, property);
CFStringRef phoneNumber = ABMultiValueCopyValueAtIndex(phones, identifier);
NSLog(@"%@", phoneNumber);
NSMutableString *tmp = [NSMutableString stringWithFormat:@"%@", (__bridge_transfer NSString *)phoneNumber];
NSString *strippedPhoneNumber = [tmp stringByReplacingOccurrencesOfString:@" " withString:@""];
NSCharacterSet *doNotWant = [NSCharacterSet characterSetWithCharactersInString:@"()-"];
strippedPhoneNumber = [[strippedPhoneNumber componentsSeparatedByCharactersInSet: doNotWant] componentsJoinedByString: @""];
NSString *firstName = (__bridge_transfer NSString *)ABRecordCopyValue(person, kABPersonFirstNameProperty);
[peoplePicker dismissViewControllerAnimated:YES completion:nil];
return NO;
}
Upvotes: 0
Reputation: 19802
You can easily iterate like that. Try NSLoging that code to make sure it works. I think you have some bugs in your "choosing" logic.
ABMultiValueRef phones = ABRecordCopyValue(person, kABPersonPhoneProperty);
for (CFIndex i=0; i < ABMultiValueGetCount(phones); i++)
{
NSString* phoneLabel = (NSString*)ABMultiValueCopyLabelAtIndex(phones, i);
NSString* phoneNumber = ABMultiValueCopyValueAtIndex(phones, i);
//release variables since you were using COPY !!!
CFRelease(phoneNumber);
CFRelease(phoneLabel);
}
CFRelease(phones);
Upvotes: 0