【发布时间】:2014-08-17 05:31:13
【问题描述】:
原始问题(参见下面的解决方案):
我正在尝试在我的 Swift 应用程序中使用 AddressBook.framework,但不知道如何实现 ABAddressBookRegisterExternalChangeCallback 函数。
在 Objective-C 中,我只是将回调实现为 C 函数并传递它的指针:
// somewhere in the initializer of the MyAddressBook class:
ABAddressBookRef addressBook = ABAddressBookCreateWithOptions(nil, nil);
ABAddressBookRegisterExternalChangeCallback(addressBook, externalChangeCallback, (__bridge void *)(self));
// somewhere else in the MyAddressBook class:
void externalChangeCallback(ABAddressBookRef reference, CFDictionaryRef info, void *context)
{
[(__bridge MyAddressBook *)context addressBookDidChangeExternally];
}
- (void)addressBookDidChangeExternally
{
// good old Obj-C from here on!
}
在 Swift 中,事实证明我很难处理 C 函数。我发现 Apple 在 beta 3 中添加了传递 C 函数指针的功能,但是我该如何声明这样的函数呢?使用 Swift 的闭包语法会很好,但在这里甚至可以吗?
这是我创建ABAddressBookRef的地方:
var addressBookRef: ABAddressBookRef = {
let addressBookRef: ABAddressBookRef = ABAddressBookCreateWithOptions(nil, nil).takeRetainedValue()
// TODO: how do I make this work?
let externalChangeCallback: ABExternalChangeCallback = {
println("Address book changed externally!")
}
ABAddressBookRegisterExternalChangeCallback(addressBookRef, externalChangeCallback, nil)
return addressBookRef
}()
那么我该如何在 Swift 中实现呢?
解决方案(有缺陷):
按照 pNre 的建议,我现在是这样实现的:
在 Objective-C 中:
AddressBookExternalChangeCallback.h:
#import <AddressBook/AddressBook.h>
void registerExternalChangeCallbackForAddressBook(ABAddressBookRef addressBookRef);
AddressBookExternalChangeCallback.m:
#import "AddressBookExternalChangeCallback.h"
void addressBookExternalChangeCallback(ABAddressBookRef addressBookRef, CFDictionaryRef info, void *context)
{
dispatch_async(dispatch_get_main_queue(), ^{
[[NSNotificationCenter defaultCenter] postNotificationName:@"AddressBookDidChangeExternallyNotification" object:nil];
});
}
void registerExternalChangeCallbackForAddressBook(ABAddressBookRef addressBookRef)
{
ABAddressBookRegisterExternalChangeCallback(addressBookRef, addressBookExternalChangeCallback, nil);
}
在 Swift 中:
导入桥接头后:
registerExternalChangeCallbackForAddressBook(addressBookRef)
只要地址簿发生更改,就会发布通知。不过,只有 @objc 类可以注册通知,所以有没有办法调用 Swift 函数或方法?
【问题讨论】:
-
那么你是怎么完成的?我确实在桥接头和类型别名 ABExternalChangeCallback = CFunctionPointer) -> Void)> 在我的 swift 类中全局声明了 registerExternalChangeCallbackForAddressBook(addressBookRef) 接下来如何在 Swift 中调用 registerExternalChangeCallbackForAddressBook ?请您发布您对 swift 的详细答案,这对像我这样的用户非常有帮助。
标签: swift abaddressbook