上一篇主要是介绍打包.a静态库的一些操作,这一篇主要介绍一下打包.framework流程。
在接下来介绍的过程中,相信你也会慢慢体会到.framework和.a在实际应用中的关系是什么,了解了它们的关系后我们会对.framework如何打包成.a和.a如何打包成.framework进行说明,最终决定将你们的项目部分组件或功能模块打包成.framework形式的静态库比较好还是.a形式的静态库比较好由个人喜好而定,区别不大,本人更喜欢使用.framework静态库,相对来说更方便一些,不用再去管那些.h文件应该放在哪里。
第一步,新建打包.framework的项目
第二步,将下载下来的SVProgressHUD文件包拖入工程,并将.bundle文件移除,原因是.bundle文件打包到.framework中,iOS系统并不会去扫描.framework下的.bundle资源文件,与打包.a库一样,.bundle资源文件需要在外部配合使用。
第三步,将需要暴露的.h文件拖拽带public区域
第四部,设置编译模式为Release模式
第五步,build settings 下的Mach-O Type 类型一定要改为 Static Library,因为苹果不支持动态库类型,.framework也属于静态库。
第六步,分别选择真机和模拟器编译一遍,会分别生成Release-iphoneos和
Release-iphonesimulator两个文件夹,文件夹下便是我们编译后生成的.framework静态库。
第七步,合并模拟器和真机的.framework静态库下的二进制文件,注意:路径要具体到二进制文件而不是.framework静态库。
1 | lipo -create /Users/[your user name]/Library/Developer/Xcode/DerivedData/DynamicSVProgressHUD-hhzxauickcqbyyaijmnejkydrnug/Build/Products/Release-iphoneos/DynamicSVProgressHUD.framework/DynamicSVProgressHUD /Users/[your user name]/Library/Developer/Xcode/DerivedData/DynamicSVProgressHUD-hhzxauickcqbyyaijmnejkydrnug/Build/Products/Release-iphonesimulator/DynamicSVProgressHUD.framework/DynamicSVProgressHUD -output /Users/[your user name]/Desktop/DynamicSVProgressHUD/DynamicSVProgressHUD |
最后将任意一个.framework下的二进制文件替换成新生成的二进制文件即可。
第八步,我们新建一个新的工程,将我们自己生成.framework静态库拖入工程,对了,别忘了把SVProgressHUD.bundle资源文件也拖入工程,接下来run一下看看效果如下:
经过这两小节的介绍我们可以发现,.framework实质就是.a + .h 组合,.a静态库也需要配合.h文件使用,只不过我们生成.framework的时候,.h已经包含到了.framework静态库里面了,而.a静态库只是一个单独的库,.h文件没有包含进去,需要配合着使用才能发挥作用。
那么,如果我们想要把.framework打包成静态库.a的形式的话,只需要把.framework中的二进制文件和.h文件拖到打包.a静态库的工程中生成新的.a静态库即可。
同理,如果.a静态库想打包成.framework静态库,也只需要把.h和.a文件拖入到打包.framework静态库的工程中生成.framework静态库即可。
打包.a和.framework静态库过程中可能会遇到问题总结
- 如果创建的framework中使用了category类,则在使用framework的项目配置中【Other Linker Flags】需要添加参数【-ObjC]或者【-all_load】
- 如果使用framework的使用出现【Umbrella header for module ‘XXXX’ does not include header ‘XXXXX.h’】,是因为错把xxxxx.h拖到了public中。
- 如果出现【dyld: Library not loaded:XXXXXX】,是因为打包的framework版本太高。比如打包framework时,选择的是iOS 9.0,而实际的工程环境是iOS 8开始的。
- 如果创建的framework类中使用了.dylib或者.tbd,首先需要在实际项目中导入.dylib或者.tbd动态库,然后需要设置build setting 中的【Allow Non-modular Includes ….】为YES,否则会报错”Include of non-modular header inside framework module”。