Swift 4
时间:2020-05-16 分类:Swift 作者:编程之家
Swift与Objective-C的兼容能力允许你在同
一个 工程中同时使用两种语言。你可以用这种叫做“mix and match”的特性来开发基于混合语言的应用。使用Swfit的最新特性--“mix and match”,你可以实现应用的一部分
功能 ,并无缝地并入已有的Objective-C的
代码 中。
Mix and Match 概述
Swift与Objective-C
文件 可以在
一个 工程中并存,不管这个工程原本是基于Objective-C还是Swift。你可以直接往现有工程中简单地
添加 另一种语言的
文件 。这种自然的工作流使得创建混合语言的应用或framework target,与用单独一种语言时一样简单。
编写混合语言的工作流程只有一点点区别,这取决于你是在写应用还是写框架。下面描述了用两种语言在
一个 target中导入模型的情况,后续章节会有更多细节。
如果你在写混合语言的应用,可能需要用Swift
代码 访问Objective-C
代码 ,或者反之。本章描述的流程适用于non-framework target。
将Objective-C导入Swift
要在同
一个 app target中导入Objective-C
文件 供Swift使用,你需要依赖Objective-C的桥接头
文件 (Objective-C bridging header)来暴露给 Swift。当你
添加 Swift
文件 到现有的Objective-C应用时,Xcode 会
自动 创建这些头
文件 ,反之亦然。
你应该编辑这个头
文件 来对Swift暴露出Objective-C
代码 。
在同一target中将Objective-C代码 导入到Swift中
1.在Objective-C桥接头
文件 中,导入任何你想暴露给 Swift 的头
文件 ,例如:
OBJECTIVE-C
#import"XYZCustomCell.h"
#import"XYZCustomView.h"
#import"XYZCustomViewController.h"
2.在Build Settings中,确保Objective-C桥接头
文件 的build setting是基于 Swfit 编译器,即Code Generation 含有头
文件 的路径。这个路径必须是头
文件 自身的路径,而不是它所在的目录。
这个路径应该是你工程的相对路径,类似 Info.plist 在 Build Settings 中指定的路径。在大多数情况下,你不需要
修改 这个设置。
在这 个桥接头
文件 中列出的所有公开的Objective-C 头
文件 都会对 Swift 可见。之后当前 target 的所有 Swift
文件 都可以使用这些头
文件 中的
方法 ,不需要任何import语句。用 Swift 语法使用这些Objective-C
代码 ,就像使用系统
自带 的类一样。
SWIFT
letmyCell=XYZCustomCell()
myCell.subtitle="Acustomcell"
将 Swift 导入Objective-C
在同一target中将Swift代码导入到Objective-C中
在相同 target 的 Objc .m 源文件中,用下面的语法来导入Swift 代码:
#import“ProductModuleName-Swift.h”
target 中任何 Swift 文件将会对 Objc .m 文件可见,包括这个 import 语句。关于在 Objc 代码中使用 Swift 代码,详见 Using Swift from Objective-C。
在同个Framework Target中导入代码
如果你在写一个混合语言的框架,可能会从 Swift 代码访问 Objc 代码,或者反之。
将 Objc 导入 Swift
要将一些 Objc 文件导入到同个框架 target 的 Swift 代码中去,你需要将这些文件导入到 Objc 的 umbrella header 来供框架使用。
在同一framework中将Objective-C代码导入到Swift中
确保将框架 target 的 Build Settings > Packaging > Defines Module 设置为 Yes 。然后在你的 umbrella header 头文件中导入你想暴露给 Swift 访问的 Objc 头文件,例如:
#import<XYZ/XYZCustomCell.h>
#import<XYZ/XYZCustomView.h>
#import<XYZ/XYZCustomViewController.h>
Swift 将会看到所有你在 umbrella header 中公开暴露出来的头文件,框架 target 中的所有 Swift 文件都可以访问你 Objc 文件的内容,不需要任何 import 语句。
将 Swift 导入 Objc
要将一些 Swift 文件导入到同个框架的 target 的 Objc 代码去,你不需要导入任何东西到umbrella header文件,而是将 Xcode 为你的Swift代码自动生成的头文件导入到你的 Obj .m 源文件去,以便在 Objc 代码中访问 Swift 代码。
在同一framework中将Swift代码导入到Objective-C中
1.确保将框架target 的 Build Settings > Packaging 中的 Defines Module 设置为 Yes 。用下面的语法将 Swift 代码导入到同个框架 target 下的 Objc .m 源文件去。
#import<ProductName/ProductModuleName-Swift.h>
导入外部 Framework
你可以导入外部框架,不管这个框架是纯 Objc,纯 Swift,还是混合语言的。import 外部框架的流程都是一样的,不管这个框架是用一种语言写的,还是包含两种语言。当你导入外部框架时,确保 Build Setting > Pakaging > Defi
nes Module 设置为 Yes 。
用下面的语法将框架导入到不同 target 的 Swift
文件 中:
import FrameworkName
用下面的语法将框架导入到不同 target 的 Objc .m
文件 中:
@import FrameworkName;
在Objective-C中使用 Swift
当你将 Swift
代码 导入 Objc
文件 之后,用普通的 Objc 语法使用 Swift 类。
MySwiftClass*swiftObject=[[MySwiftClassalloc]init];
[swiftObjectswiftMethod];
Swift 的类或协议必须用 @objc attribute 来
标记 ,以便在 Objc 中可访问。这个 attribute 告诉编译器这个 Swift
代码 可以从 Objc
代码 中访问。如果你的 Swift 类是 Objc 类的子类,编译器会
自动 为你
添加 @objc attribute 。详见
Swift Type Compatibility 。
你可以访问 Swift 类或协议中用 @objc attribute
标记 过东西,只要它和 Objc 兼容。不
包括 一下这些 Swift 独有的特性:
Generics - 范型
Enumerations defined in Swift - Swift 中定义的枚举
Structures defined in Swift - Swift 中定义的结构体
Top-level functions defined in Swift - Swift Swift 中定义的顶层函数
Global variables defined in Swift - Swift 中定义的全局变量
Typealiases defined in Swift - Swift 中定义的类型别名
Swift-style variadics
Curried functions - 柯里化后的函数
例如带有范型类型作为参数,或者返回
元组 的
方法 不能在Objective-C中使用。
为了避免循环引用,不要将 Swift
代码 导入到Objective-C头
文件 中。但是你可以在Objective-C头
文件 中前向声明( forward declare )
一个 Swift 类来使用它,然而,注意不能在Objective-C中继承
一个 Swift 类。
这样前向声明 Swift 类:
//MyObjccl ass.h
@class MySwiftClass;
@interface MyObjccl ass:NSObject
-(MySwiftClass*)returnSwiftObject;
/*...*/
@end
Product Module命名
Xcode 为 Swift
代码 生成 的头
文件 的
名称 ,以及 Xcode 创建的 Objc 桥接头
文件 名称 ,都是从你的 product 模块名
生成 的。
默 认你的 product 模块名和 product 名一样。然而,如果你的 product 名有特殊字符(nonalphanumeric,非数字、字母的字符),例如点号,那么它们会被下划线( _ )替换之后作为你的 product 模块名。如果 product 名以数字开头,那么第
一个 数字会用下划线替换掉。
你可以给 product 模块名提供
一个 自定义 的
名称 ,Xcode 会用这个
名称 来命名桥接的和
自动 生成 的头
文件 。你只需要在
修改 在 build setting 中的 Product Module Name 即可。
故障排除和提醒
•把 Swift 和 Objc
文件 看作相同的
代码 集合,并注意命名冲突;
•如果你用框架,确保 Build Setting > Pakaging > Defi
nes Module 设置为 Yes ;
•如果你使用 Objc 桥接头
文件 ,确保在 Build Settings 中 Objc 桥接头
文件 的 build setting 是基于 Swfit 编译器,即 Code Generation 含有头
文件 的路径。这个路径必须是头
文件 自身的路径,而不是它所在的目录。
•为了在 Objc 中可用, Swift 类必须是 Objc 类的子类,或者用 @objc
标记 ;
•如果你在 Swift
代码 中使用你自己的 Objc 类型,确保先将对应的 Objc 头
文件 导入到你的 Swift
代码 中,然后才将 Swift
自动 生成 的头
文件 import 到 Objc .m 源
文件 中来访问 Swift
代码 。
原文地址:https://www.jb51.cc/swift/327350.html
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。