[英]Create swift closure and pass it to objective-c class as completion block
Now I'm adding Swift code on objective-C based iOS application. 现在,我在基于Objective-C的iOS应用程序上添加Swift代码。
But I have a problem in calling the objective-C method from Swift side. 但是从Swift方面调用Objective-C方法时遇到问题。
I'd like to get and draw image on UIImageView
in View
or ViewController
which is written with Swift. 我想在用Swift编写的View
或ViewController
UIImageView
上获取和绘制图像。 On the other hand my wrapper class of Photos Library is written with objective-C. 另一方面,我的照片库包装器类是用Objective-C编写的。
My wrapper class of Photos Library is below. 我的照片库包装器类如下。
・MyPhotoLibraryMgr.h ・ MyPhotoLibraryMgr.h
typedef void (^AppPhotoLibraryGetImageCompletion)(UIImage *image, NSError *error);
- (void)getImageWithTarget:(NSInteger)index
targetSize:(CGSize)targetSize
completion:(AppPhotoLibraryGetImageCompletion)completion;
・MyPhotoLibraryMgr.m ・ MyPhotoLibraryMgr.m
- (void)getImageWithTarget:(NSInteger)index
targetSize:(CGSize)targetSize
completion:
(AppPhotoLibraryGetImageCompletion)completion
{
PHAsset *asset = _myAsetsList[index];
PHImageRequestOptions *options = [[PHImageRequestOptions alloc] init];
options.resizeMode = PHImageRequestOptionsResizeModeFast;
options.deliveryMode = PHImageRequestOptionsDeliveryModeOpportunistic;
[[PHImageManager defaultManager] requestImageForAsset:asset
targetSize:targetSize
contentMode:PHImageContentModeAspectFill
options:options
resultHandler:^(UIImage *result, NSDictionary *info) {
NSError *error = [info objectForKey:PHImageErrorKey];
if (error) {
NSLog(@"error=%@", error);
}
completion(result, error);
}];
}
I can get and draw image in View
or ViewController
written by objective-C like below, 我可以在由Objective-C编写的View
或ViewController
获取并绘制图像,如下所示,
・MyViewController.m ・ MyViewController.m
AppPhotoLibraryMgr *photoLibMgr = [AppPhotoLibraryMgr sharedInstance];
AppPhotoLibraryGetImageCompletion completion = ^(UIImage *image, NSError *error) {
imageView.image = image;
};
[[AppPhotoLibraryMgr sharedInstance] getImageWithTarget:index
targetSize:imageView.frame.size
completion:completion];
But I can't get image in View
or ViewController
written in Swift. 但是我无法在用Swift编写的View
或ViewController
获得图像。
・MySwiftViewController.swift ・ MySwiftViewController.swift
let completion = {(image: UIImage, error: NSError) -> AppPhotoLibraryGetImageCompletion in
let imageView = UIImageView(image: image)
}
photoLibMgr?.getImageWithTarget(index, targetSize: size, completion: completion)
Error message from Xcode is 来自Xcode的错误消息是
Cannot convert value of type 'UIImage, NSError -> AppPhotoLibraryGetImageCompletion" to expected argument type 'AppPhotoLibraryGetImageCompletion' 无法将类型'UIImage,NSError-> AppPhotoLibraryGetImageCompletion'的值转换为预期的参数类型'AppPhotoLibraryGetImageCompletion'
The block typedef void (^AppPhotoLibraryGetImageCompletion)(UIImage *image, NSError *error);
块typedef void (^AppPhotoLibraryGetImageCompletion)(UIImage *image, NSError *error);
in objective-c has return type void
. 在Objective-C中,返回类型为void
。
But the counter part in your Swift has return type other than Void
. 但是Swift中的计数器部分具有Void
以外的返回类型。 The completion block should be like: 完成块应类似于:
let completion = {(image: UIImage, error: NSError) -> Void in
...
...
}
Use typealias
for making your closure reusable. 使用typealias
使封闭可重用。
Example: 例:
typealias AppPhotoLibraryGetImageCompletion = (UIImage, NSError) -> Void
let completion: AppPhotoLibraryGetImageCompletion = { (image, error) in
...
...
}
Edit: Different way 编辑:不同的方式
photoLibMgr?.getImageWithTarget(index, targetSize: size, completion: { (image, error) in
...
...
})
Your declaration of completion
variable is wrong in MySwiftViewController.swift file. 您的completion
声明变量在MySwiftViewController.swift文件中是错误的。
Edit it like this: 像这样编辑它:
let completion: AppPhotoLibraryGetImageCompletion = { (image, error) in
let imageView = UIImageView(image: image)
}
OR 要么
If you don't want to declare completion handler as variable, then simply do the: 如果您不想将完成处理程序声明为变量,则只需执行以下操作:
LinphoneLoginController.shared().getImageWithTarget(index, targetSize: size) { (image, error) in
let imageView = UIImageView(image: image)
}
It should be typedef
instead of Typedef
. 它应该是typedef
而不是Typedef
。 Move typedef
on top of interface declare and don't declare it again: 将typedef
移动到接口声明的顶部,然后不再声明:
typedef void (^AppPhotoLibraryGetImageCompletion)(UIImage *image, NSError *error);
@interface MyPhotoLibraryMgr....
After the changes it should work similar in Swift
, auto complete will change your AppPhotoLibraryGetImageCompletion
to (image, error) {..}
更改后,它应在Swift
类似地工作,自动完成将把您的AppPhotoLibraryGetImageCompletion
更改为(image, error) {..}
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.