请参阅Apple的使用Swift与Cocoa和Objective-C的指南.本指南介绍了如何使用Swift中的Objective-C和C代码,反之亦然,并提供了如何在现有项目中转换项目或混合和匹配Objective-C/C和Swift部件的建议.
编译器自动生成Swift语法,用于调用C函数和Objective-C方法.如文档中所示,此Objective-C:
UITableView *myTableView = [[UITableView alloc] initWithFrame:CGRectZero style:UITableViewStyleGrouped];
变成这个Swift代码:
let myTableView: UITableView = UITableView(frame: CGRectZero, style: .Grouped)
Xcode也可以动态执行此转换 - 您可以在编辑Swift文件时使用Open Quickly并键入Objective-C类名称,它将带您进入类标题的Swift-ified版本.(您也可以通过cmd单击Swift文件中的API符号来获取此信息.)并且在Objective-C和Swift中都可以看到iOS 8和OS X v10.10(Yosemite)开发人员库中的所有API参考文档.表格(例如UIView
).
**如果您有要使用的现有课程,请执行步骤2,然后跳到步骤5.(在某些情况下,我必须在#import <Foundation/Foundation.h
旧的Objective-C文件中添加一个显式内容.)**
将.m
文件添加到您的类中,并为其命名CustomObject.m
.
添加.m
文件时,您可能会遇到如下提示:
单击是!
如果您没有看到提示或意外删除了桥接标题,请将新.h
文件添加到项目中并命名<#YourProjectName#>-Bridging-Header.h
.
在某些情况下,特别是在使用Objective-C框架时,您不会显式添加Objective-C类,Xcode也无法找到链接器.在这种情况下,创建.h
如上所述命名的文件,然后确保在目标的项目设置中链接其路径,如下所示:
注意
最好使用$(SRCROOT)
宏链接项目,这样,如果您移动项目,或者使用远程存储库与其他人一起工作,它仍然可以工作.$(SRCROOT)
可以被认为是包含.xcodeproj文件的目录.它可能看起来像这样:
$(SRCROOT)/Folder/Folder/<#YourProjectName#>-Bridging-Header.h
添加另一个.h
文件并命名CustomObject.h
.
在 CustomObject.h
#import <Foundation/Foundation.h> @interface CustomObject : NSObject @property (strong, nonatomic) id someProperty; - (void) someMethod; @end
在 CustomObject.m
#import "CustomObject.h" @implementation CustomObject - (void) someMethod { NSLog(@"SomeMethod Ran"); } @end
在YourProject-Bridging-Header.h
:
#import "CustomObject.h"
在SomeSwiftFile.swift
:
var instanceOfCustomObject: CustomObject = CustomObject() instanceOfCustomObject.someProperty = "Hello World" println(instanceOfCustomObject.someProperty) instanceOfCustomObject.someMethod()
无需明确导入; 这就是桥接头的用途.
将.swift
文件添加到项目中,并为其命名MySwiftObject.swift
.
在MySwiftObject.swift
:
import Foundation class MySwiftObject : NSObject { var someProperty: AnyObject = "Some Initializer Val" init() {} func someFunction(someArg:AnyObject) -> String { var returnVal = "You sent me \(someArg)" return returnVal } }
在SomeRandomClass.m
:
#import "<#YourProjectName#>-Swift.h"
文件:<#YourProjectName#>-Swift.h
应该已经在项目中自动创建,即使您看不到它.
MySwiftObject * myOb = [MySwiftObject new]; NSLog(@"MyOb.someProperty: %@", myOb.someProperty); myOb.someProperty = @"Hello World"; NSLog(@"MyOb.someProperty: %@", myOb.someProperty); // original NSString * retString = [myOb someFunction:@"Arg"]; // xcode10 expands the external arg here NSString * retString = [myOb someFunctionWithSomeArg:@"Arg"];| NSLog(@"RetString: %@", retString);
1. CodeCompletion的表现并不像我想的那样准确.在我的系统上,使用"cmd + r"运行快速构建似乎有助于Swift找到一些Objective-C代码,反之亦然.
2.如果您将.swift
文件添加到较旧的项目并收到错误:dyld: Library not loaded: @rpath/libswift_stdlib_core.dylib
,请尝试完全重新启动Xcode.
3.虽然最初可以通过使用@objc
前缀在Objective-C中使用纯Swift类,但在Swift 2.0之后,这已不再可能.有关原始说明,请参阅编辑历史 如果在将来的Swift版本中重新启用此功能,则答案将相应更新.
以下是在Swift项目中使用Objective-C代码(在本例中为第三方提供的框架)的分步说明:
通过选择File - > New - > New File - > Objective-C File,将任何Objective-C文件添加到Swift项目中.保存后,Xcode会询问您是否要添加桥接标头.选择" 是 ".Gif:将空文件添加到项目并生成桥接头http://www.derrrick.com/stackoverflow/1-empty-file.gif
简单的步骤:
出现提示,然后单击确定...如果没有出现,则我们手动创建它,如下所示...从iOS源创建一个头文件并命名为ProjectName-Bridging-Header(示例:Test -Bridging-Header),然后转到Swift编译器代码中的构建设置 - > Objective-C bridge添加Objective-C桥接名称..(Test/Test-Bridging-Header.h).是的,那是完整的.
(可选)删除您添加的Objective-C文件(在上面的GIF图像中命名为"任何内容").你不再需要它了.
打开桥接头文件 - 文件名的格式为[YourProject] -Bridging-Header.h.它包括Xcode提供的评论.为要包含的Objective-C文件添加一行代码,例如第三方框架.例如,要将Mixpanel添加到项目中,您需要将以下代码行添加到桥接头文件中:
#import "Mixpanel.h"
现在在任何Swift文件中,您都可以使用现有的Objective-C代码,在Swift语法中(在本例中,您可以调用Mixpanel SDK方法等).您需要熟悉Xcode如何将Objective-C转换为Swift.Apple的指南快速阅读.或者查看此答案以获得不完整的摘要.
Mixpanel的示例:
func application(application: UIApplication, didFinishLaunchingWithOptions launchOptions: [NSObject: AnyObject]?) -> Bool { Mixpanel.sharedInstanceWithToken("your-token") return true }
而已!
注意:如果从项目中删除桥接头文件,请务必进入构建设置并删除"Swift编译器 - 代码生成"下的" Objective-C Bridging Header " 的值.
创建桥接标头后,转到Build Setting => Search for"Objective-C Bridging Header".
在下面你会发现""Objective-C Generated Interface Header Name"文件.
在视图控制器中导入该文件.
示例:在我的情况下:"Dauble-Swift.h"
你可以阅读好文章Swift和Cocoapods.基本上,我们需要创建一个桥接头文件并将所有Objective-C头放在那里.然后我们需要从构建设置中引用它.之后,我们可以使用Objective-C代码.
let manager = AFHTTPRequestOperationManager() manager.GET( "http://example.com/resources.json", parameters: nil, success: { (operation: AFHTTPRequestOperation!, responseObject: AnyObject!) in println("JSON: " + responseObject.description) }, failure: { (operation: AFHTTPRequestOperation!, error: NSError!) in println("Error: " + error.localizedDescription) })
另请参阅Apple的文档使用Swift与Cocoa和Objective-C.
对于试图向Swift添加Objective-C库的人来说只是一个注释:你应该在Build Settings - > Linking - > Other Linker Flags中添加-ObjC.
我写了一个简单的Xcode 6项目,展示了如何混合使用C++,Objective-C和Swift代码:
https://github.com/romitagl/shared/tree/master/C-ObjC-Swift/Performance_Console
特别是,该示例从Swift调用Objective-C和C++函数.
关键是创建一个共享头,Project-Bridging-Header.h,并将Objective-C头放在那里.
请下载该项目作为完整示例.
从文档中引用:
任何可作为模块访问的Objective-C框架(或C库)都可以直接导入Swift.这包括所有Objective-C系统框架 - 例如Foundation,UIKit和SpriteKit - 以及随系统提供的通用C库.例如,要导入Foundation,只需将此import语句添加到您正在使用的Swift文件的顶部:
import Foundation
此导入使所有Foundation API(包括NSDate,NSURL,NSMutableData及其所有方法,属性和类别)直接在Swift中可用.
我非常感谢@ Logan的回答.创建桥文件和设置有很大帮助.
但是在完成所有这些步骤后,我仍然没有在Swift中获得Objective-C类.
我使用了cocoapods
库并将其集成到我的项目中.这是pod "pop"
.
因此,如果你在Swift中使用Objective-C pod,那么你可能无法import
将类或类转换为Swift.
你要做的很简单的事情是:
转到<YOUR-PROJECT>-Bridging-Header
文件和
将语句替换#import <ObjC_Framework>
为@import ObjC_Framework
例如:(流行库)
更换
#import <pop/POP.h>
同
@import pop;
clang import
在#import
不工作时使用.
请参阅Apple的使用Swift与Cocoa和Objective-C的指南.本指南介绍了如何使用Swift中的Objective-C和C代码,反之亦然,并提供了如何在现有项目中转换项目或混合和匹配Objective-C/C和Swift部件的建议.
编译器自动生成Swift语法,用于调用C函数和Objective-C方法.如文档中所示,此Objective-C:
UITableView *myTableView = [[UITableView alloc] initWithFrame:CGRectZero style:UITableViewStyleGrouped];
变成这个Swift代码:
let myTableView: UITableView = UITableView(frame: CGRectZero, style: .Grouped)
Xcode也可以动态执行此转换 - 您可以在编辑Swift文件时使用Open Quickly并键入Objective-C类名称,它将带您进入类标题的Swift-ified版本.(您也可以通过cmd单击Swift文件中的API符号来获取此信息.)并且在Objective-C和Swift中都可以看到iOS 8和OS X v10.10(Yosemite)开发人员库中的所有API参考文档.表格(例如UIView
).