转载http://daipei.me/posts/make_framework_by_xcode8/
前言
网上关于Framework制作的教程数不胜数,然而都过于陈旧,最新的也是使用Xcode7的教程,而且有些设置也只给出步骤,并没有给出原因,而且按照有些教程制作出的framework还有些问题,所以我把自己制作framework的过程记录下来,并且使用的是最新的Xcode8环境。
正文
首先新建一个项目,选择Cocoa touch Framework
然后随便取一个名字
然后将要封装成framework的代码拖入工程
选择工程文件>target第一项>Build Setting>搜索linking,然后几个需要设置的选项都显现出来,首先是Dead Code Stripping设置为NO,网上对此项的解释如下,大致意思是如果开启此项就会对代码中的”dead”、”unreachable”的代码过滤,不过这个开关是否关闭,似乎没有多大影响,不过为了完整还原framework中的代码,将此项关闭也未曾不可。
The resulting executable will not include any “dead” or unreachable code
然后将Link With Standard Libraries关闭,我想可能是为了避免重复链接
最后将Mach-O Type设为Static Library,framework可以是动态库也可以是静态库,对于系统的framework是动态库,而用户制作的framework只能是静态库。
然后将需要公开的头文件从Project中拖入Public,至于是否需要将私有的头文件拖入Private,我觉得直接放在Project中即可,若是Private中有头文件,打包以后的framework中会多出一个Private的文件夹包含着放入Private的头文件,不过我觉得如果是私有最好还是不要让别人看到。
为了对一些特殊机型的支持,添加armv7s架构,当然不添加也没什么问题,只有5和5c使用了此架构。
下面就开始编译了,先选择Generic iOS Device,按下Command+B:Build一下
然后随意选择一个模拟器再次Build一下
找到Build后的framework
我们看到总共有两个文件夹,上面是真机编译生成的文件,下面是模拟器编译生成的文件。
然后用命令行将下面两个文件进行合成
将合成后的文件输出到桌面之上,这里解释一下这看似很复杂的命令:lipo -create
+上面两个文件的路径 + -output
+ 合成后文件的输出路径
然后用输出在桌面上的YuXinSDK替换掉前面Debug-iphoneos中framework中的YuXinSDK
将这做好的framework直接拖入要使用的工程中
注意将Copy items if needed打勾
然后在工程的search path中加上此framework的Headers的路径
本以为大功告成,按下了Command+R悠闲的等着编译运行,然而在链接的时候却出了问题
很经典的错误,库中缺少了i386架构的文件,这时我就比较困惑了,明明将模拟器生成的库文件合并进来了,怎么在模拟器上编不通呢!用lipo命令查看一下,果然没有i386架构的文件
再看一下用模拟器生成的framework
居然只有x86_64架构
我换成iPhone 4s模拟器,编译后生成的文件居然包含了i386
经过我的测试,在iPhone5之前编译的framework都是i386架构,iPhone 5s之后都是x86_64架构,然而在所有模拟器上运行时,这两种架构缺一不可,然后我将这两种架构的framework合并在与真机的合并
拖入工程后终于能够正常运行了
后来经过摸索发现之前按照网上的教程却把自己坑了
开始将上图中的选项设为YES,导致其编译时只生成当前机器的框架,将其设置为NO后,发现用模拟器编译后生成的framework同时包含x86_64和i386架构。
bitCode错误
在项目中引入静态库后,archive的时候又会出现错误
bitcode bundle could not be generated because ... was built without full bitcode.All object files and libraries for bitcode must be generated from Xcode Archive or Install build for architecture arm64 |
Bitcode是苹果在Xcode7及以后推出的新功能。用于代码的二次编译,针对CPU进行优化,编译工作由苹果AppStore后台来完成。
针对iOS是可选项,默认打开。watchOS 和 tvOS 是必选项。
所以需要打开库工程的此选项并加上-fembed-bitcode参数,重新编译
如此archive时就不会出问题了,到此我在制作使用framework时遇到的问题都在这里了。
总结
架构
对于模拟器来说4s和5的模架构是i386的32位架构,5s至今是x86_64的64位架构。对于真机来说3GS~4s是armv7架构,5和5c是armv7s架构,5s至今是arm64架构
静态库
静态库: 链接时完整地拷贝至可执行文件中,被多次使用就有多份冗余拷贝。
动态库
动态库:链接时不会拷贝至可执行文件中,运行时动态加载进内存,供程序调用,只加载一次,多个程序可以共用。
我已经将代码上传到github上,这里给出地址:https://github.com/948080952/YuXinSDK
此篇博客中参考了的博客:https://my.oschina.net/kaqijiang/blog/649632