从 Objective-C 类调用 Swift 函数
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/24078043/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Call Swift function from Objective-C class
提问by Eloreden
I have an old Objective-C project and I want to call new Swift function and object, I have create the file "<ProjectName>-Bridging-Header.h" and "<ProjectName>-Swift.h"
我有一个旧的 Objective-C 项目,我想调用新的 Swift 函数和对象,我已经创建了文件“ <ProjectName>-Bridging-Header.h”和“ <ProjectName>-Swift.h”
was easy for me call the function from Swift to Objective-C but I have a problem for reverse.
对我来说,从 Swift 调用函数到 Objective-C 很容易,但我有一个反向问题。
So I have create a simple class "System.Swift"
所以我创建了一个简单的类“System.Swift”
import Foundation
@objc class System : NSObject {
@objc func printSome() {
println("Print line System");
}
}
now I have try to follow the documentation hereand inside the <...>-Swift.hfile I have write this
现在我尝试按照文档here和<...>-Swift.h我写的文件里面
@class System;
@interface System : NSObject
-(void)printSome;
@end
and I have import it inside my Objective-C Class. At this point inside my Objective C class (currently UIViewController) of my Objective-C code I have try to call "printSome" method:
我已经将它导入到我的 Objective-C 类中。此时,在我的 Objective-C 代码的 Objective C 类(当前为 UIViewController)中,我尝试调用“printSome”方法:
- (void)viewDidLoad
{
[super viewDidLoad];
System * sis = [[System alloc] init];
[sis printSome];
//any additional setup after loading the view from its nib.
}
now I have the following Error:
现在我有以下错误:
Undefined symbols for architecture i386: "_OBJC_CLASS_$_System", referenced from: objc-class-ref in "ObjectiveC_Class_That_Call_Swift_Object".o ld: symbol(s) not found for architecture i386 clang: error: linker command failed with exit code 1 (use -v to see invocation)
体系结构 i386 的未定义符号:“_OBJC_CLASS_$_System”,引用自:“ObjectiveC_Class_That_Call_Swift_Object”中的 objc-class-ref。 -v 查看调用)
采纳答案by Eloreden
Problem Solved, I previously create and included a new .hfile in my Objective-Cclass named <ProductModuleName>-Swift.hbut, as i discovered later, this step is not necessary because the compiler creates the necessary file invisible.
问题解决了,我之前.h在我的Objective-C类中创建并包含了一个名为的新文件,<ProductModuleName>-Swift.h但是,正如我后来发现的,这一步不是必需的,因为编译器创建了不可见的必要文件。
Simply include <ProductModuleName>-Swift.hin your class and it should work.
只需包含<ProductModuleName>-Swift.h在您的班级中,它就可以工作。
回答by Svitlana
Yes Thanks
是啊谢谢
it is strange but it'll work
这很奇怪,但它会起作用
1) Add @objc to Swift class
2) Add in .m
#import "(ProjectName)-Swift.h"
3) Call from .h
@class SwiftClass;
4)On SwiftClass
click "Command" + Left Click (Apple Documantation)
5) To see "-Swift.h" -> click "Command" + Left Click
App will generate the interface for this class in -Swift.h
App 会在 -Swift.h 中为这个类生成接口
Example: SWIFT_CLASS("_TtC10Project17220PLHelper") @interface PLHelper
示例:SWIFT_CLASS("_TtC10Project17220PLHelper") @interface PLHelper
- (void)notifyForDownloading:(NSDictionary *)userInfo;
- (instancetype)init OBJC_DESIGNATED_INITIALIZER; @end
- (void)notifyForDownloading:(NSDictionary *)userInfo;
- (instancetype)init OBJC_DESIGNATED_INITIALIZER; @结尾
回答by Anubhav Giri
Assume We have ProjectName "MyFirstProjectOnSwift" and swift class name "mySwiftClass" and objectiveC class is "MyObjectiveCLass"
假设我们有 ProjectName "MyFirstProjectOnSwift" 和 swift 类名 "mySwiftClass",objectiveC 类是 "MyObjectiveCLass"
Following steps are:-
以下步骤是:-
Add #import "MyFirstProjectOnSwift-Swift.h" in "MyObjectiveCLass.m"
Add @class mySwiftClass in MyObjectiveCLass.h;
Then in MyObjectiveCLass.m
mySwiftClass *myClass = [mySwiftClass new]; {Call Like This in any method wherever you want to call swift method.}
[myClass methodName];
在“MyObjectiveCLass.m”中添加#import“MyFirstProjectOnSwift-Swift.h”
在 MyObjectiveCLass.h 中添加 @class mySwiftClass;
然后在 MyObjectiveCLass.m
mySwiftClass *myClass = [mySwiftClass 新]; {Call Like This in any method where you want to call swift method.}
[我的类方法名称];
回答by Darius Miliauskas
Check the -Swift.h file which has the import on your .m file in objective-C:
检查 -Swift.h 文件,该文件在 Objective-C 中对 .m 文件进行了导入:
#import <YourProjectName-Swift.h>
Click on that line, and left-click - Jump To Definition.
单击该行,然后左键单击 - 跳转到定义。
This file should be included automatically, not manually.
此文件应自动包含,而不是手动包含。
回答by Bryan P
If you're still not seeing your class even after importing <ProductModuleName>-Swift.h.
如果您在导入<ProductModuleName>-Swift.h.
Make sure that your class is subclassing a native class (e.g UIViewController) or at least if it's just a utility class, make it subclass NSObject. Your class should now show.
确保您的类是本地类(例如UIViewController)的子类,或者至少如果它只是一个实用程序类,请将其子类化NSObject。你的类现在应该显示。
回答by Kqtr
Little additional tip for anyone stumbling upon this post and for hwhom the other answers do not work: you might also have to declare your Swift class "public".
对于任何在这篇文章中绊倒的人以及其他答案不起作用的人来说,还有一点额外的提示:您可能还必须将 Swift 类声明为“公开”。
Example:
例子:
@objc public class MySwiftClass: NSObject {
@objc public class MySwiftClass: NSObject {
回答by Javier Calatrava Llavería
The recomended way for executing Swift code from Objective-C on projects that are being migrated from Obj-C to Swift is using Bridge/Proxy pattern.
在从 Obj-C 迁移到 Swift 的项目上从 Objective-C 执行 Swift 代码的推荐方法是使用桥接/代理模式。
- Implement the Bridge.
- 实施桥梁。
import Foundation
import Foundation
@objc class AnalyticsPropertyBridge: NSObject {
@objc class AnalyticsPropertyBridge: NSObject {
private var analytics: AnalyticsManager = AnalyticsManager()
@objc func refreshProperties() {
self.analytics.set(AnalyticsProperty.clientType)
}
}
}
- Include the objC caller module in the umbrella file (Bridging-Header):
- 在伞文件(Bridging-Header)中包含 objC 调用程序模块:
#import "CallerModule.h"
#import "CallerModule.h"
- Finally in the caller .m file, two issues:
- 最后在调用者 .m 文件中,有两个问题:
3.a Import umbrella file:
3.a 导入伞文件:
#import "MyProject-Swift.h"
#import "MyProject-Swift.h"
3.b Call the bridge.
3.b 呼叫网桥。
[[AnalyticsPropertyBridge new] refreshProperties];
[[AnalyticsPropertyBridge new] refreshProperties];
Benefits: Your swift code will not get dirty with @objc because code is being called from Objc. As time goes by, the ObjC will be reduced in your project and finally the bride will be removed.
好处:你的 swift 代码不会被 @objc 弄脏,因为代码是从 Objc 调用的。随着时间的推移,你的项目中的 ObjC 会减少,最后新娘会被移除。

