本文參考文章:iOS Xcode9 封裝生成.framework - CocoaChina_讓移動開發(fā)更簡單
1.什么是庫凸郑?
庫是共享代碼的方式分成靜態(tài)庫和動態(tài)庫
靜態(tài)庫(.a和framework):鏈接時完整的拷貝到可執(zhí)行文件永高,被多次使用就有多份冗余拷貝(我們自己建的framework是靜態(tài)庫 )
動態(tài)庫(.dylib和framework):鏈接時不拷貝,程序運行時由系統(tǒng)直接加載到內(nèi)存,供程序調(diào)用,系統(tǒng)只加載一次,多個程序共用箱亿,節(jié)省內(nèi)存。(系統(tǒng)的framework是動態(tài)庫?)
2. Framework與.a文件的區(qū)別杜漠?
.a文件是一個純二進制的文件极景, 不能直接使用,至少要跟.h文件配合使用
framework除了二進制文件還有資源文件驾茴,可以直接使用盼樟,.a+.h+sourceFile=framework
建議使用framework
3.為什么要使用靜態(tài)庫?
1 方便共享代碼锈至,便于合理使用晨缴。
2 實現(xiàn)iOS程序的模塊化∠考瘢可以把固定的業(yè)務(wù)模塊化成靜態(tài)庫击碗。
3 和別人分享你的代碼庫筑悴,但不想讓別人看到你代碼的實現(xiàn)。
4 開發(fā)第三方sdk的需要稍途。
4.制作靜態(tài)庫時的幾點注意:
1 注意理解:無論是.a靜態(tài)庫還.framework靜態(tài)庫阁吝,我們需要的都是二進制文件+.h+其它資源文件的形式,不同的是械拍,.a本身就是二進制文件突勇,需要我們自己配上.h和其它文件才能使用,而.framework本身已經(jīng)包含了.h和其它文件坷虑,可以直接使用甲馋。
2 圖片資源的處理:兩種靜態(tài)庫,一般都是把圖片文件單獨的放在一個.bundle文件中迄损,一般.bundle的名字和.a或.framework的名字相同定躏。.bundle文件很好弄,新建一個文件夾芹敌,把它改名為.bundle就可以了痊远,右鍵,顯示包內(nèi)容可以向其中添加圖片資源党窜。
3 category是我們實際開發(fā)項目中經(jīng)常用到的拗引,把category打成靜態(tài)庫是沒有問題的,但是在用這個靜態(tài)庫的工程中幌衣,調(diào)用category中的方法時會有找不到該方法的運行時錯誤(selector not recognized),解決辦法是:在使用靜態(tài)庫的工程中配置other linker flags的值為-ObjC壤玫。
4 如果一個靜態(tài)庫很復(fù)雜豁护,需要暴露的.h比較多的話,就可以在靜態(tài)庫的內(nèi)部創(chuàng)建一個.h文件(一般這個.h文件的名字和靜態(tài)庫的名字相同)欲间,然后把所有需要暴露出來的.h文件都集中放在這個.h文件中楚里,而那些原本需要暴露的.h都不需要再暴露了,只需要把.h暴露出來就可以了
從上面我們可以看出.a 和.framework的區(qū)別就是.a+.h+soureFile=.framework猎贴,這樣的話班缎,我們還是直接封裝個.framework比較好
封裝framework步驟
1、打開xcode她渴,新建工程
這里我使用的是Xcode9达址,選擇Cocoa Touch Framework,然后點next
2趁耗、創(chuàng)建功能類或者拖入已有的功能類
這里我創(chuàng)建的是ShowResult類沉唠。
3、實現(xiàn)功能類的功能
.h文件中
.m文件中
4苛败、更改Xcode項目配置
在TARGETS下選中工程>Build Setting>搜索linking满葛,然后幾個需要設(shè)置的選項都顯現(xiàn)出來径簿。
1、首先是Dead Code Stripping設(shè)置為NO嘀韧,網(wǎng)上對此項的解釋如下篇亭,大致意思是如果開啟此項就會對代碼中的”dead”、”unreachable”的代碼過濾锄贷,不過這個開關(guān)是否關(guān)閉暗赶,似乎沒有多大影響,不過為了完整還原framework中的代碼肃叶,將此項關(guān)閉也未曾不可蹂随。
2、然后將Link With Standard Libraries關(guān)閉因惭,我想可能是為了避免重復(fù)鏈接
3岳锁、最后將Mach-O Type設(shè)為Static Library,framework可以是動態(tài)庫也可以是靜態(tài)庫蹦魔,對于系統(tǒng)的framework是動態(tài)庫激率,而用戶制作的framework只能是靜態(tài)庫。
5勿决、增加armv7s
更改后:
設(shè)置Headers
將你要公開的頭文件拖至Public下乒躺,要隱藏的放在Private或者Project下,當(dāng)然低缩,隱藏的頭文件就無法再被引用嘉冒。
然后需要在FrameworkTest.h(必須是公開的,否則無法引用)中將你所有要公開的.h引入咆繁。
打包
打包有兩種方式 一種是手動打包讳推,另一種是用腳本,這里我用手動打包的方式玩般。
1银觅、選中模擬器,編譯程序command+B
2坏为、選中測試機究驴,編譯程序command+B
3、在finder中找到framework文件
找到下圖中的FrameworkTest文件匀伏,這里有兩個同名文件洒忧,一個是Debug-iphoneos(真機)下的,一個是Debug-iphonesimulator(模擬器)下的帘撰。
4跑慕、通過終端命令將兩個framework合為一個模擬器和真機都可使用的framework。
打開終端,輸入lipo -create命令核行,將
Debug-iphoneos下FrameworkTest.framework目錄下的FrameworkTest文件
拖拽到終端中牢硅,會自動有空格。然后將Debug-iphonesimulator下FrameworkTest.framework目錄下的FrameworkTest文件
拖拽進來芝雪,也會自動有空格减余,然后輸入 -output,敲空格惩系,在引入一個新的路徑位岔。最后敲回車,這樣就合并了堡牡。
上面這段命令就是把真機和模擬器中的FrameworkTest合并成一個新的文件放在和newTest同級的文件夾new下抒抬,這個新文件后綴是.lipo,并不是我們要的FrameworkTest文件晤柄,怎么辦呢擦剑?我們的操作是按照人家說的把合成后的文件名字改成FrameworkTest替換原來的。而且芥颈,把后綴.lipo去掉惠勒!然后將新生成的這個FrameworkTest替換?原來的FrameworkTest(是指同時替換掉模擬器跟真機里面的FrameworkTest文件)。進行下一步爬坑。
這里終端會有一個error
error: /Applications/Xcode.app/Contents/Developer/Toolchains/XcodeDefault.xctoolchain/usr/bin/lipo: can't move temporary file: /Users/lgj/Desktop/new/newTest to file: /Users/lgj/Desktop/new/newTest.lipo (Is a directory)
5纠屋、將修改后的framework拷貝出來就是我們最終制作的framework了。
使用
將我們封裝的framework拖拽到新的工程里面盾计。
我們打開這個framework看看售担,發(fā)現(xiàn)只有Headers,里面有兩個.h闯估,其中一個是FrameworkTest.h另一個就是ShowResult.h文件灼舍。
引入頭文件:
運行得到[ShowResult show];的結(jié)果
至此,完成framework的封裝和使用涨薪。
總結(jié)
1、在制作framework或者lib的時候炫乓,如果使用了category刚夺,則使用改FMWK的程序運行時會crash,此時需要在該工程中 other linker flags添加兩個參數(shù) -ObjC -all_load末捣。(這點沒有親測)
2侠姑、帶有圖片資源的需要把圖片打包成Bundle文件,和framework一起拷貝到相應(yīng)的項目中箩做。
3莽红、公開的類中如果引用的private的類,打包以后對外會報錯,找不到那個private的類安吁,可以把那個private的.h放到(也沒親測)
4醉蚁、namespace 沖突。靜態(tài)庫用了某第三方庫鬼店,項目也用了同樣的第三方庫网棍,在編譯的時候就會有 duplicate symbol 錯誤,因為有兩份同樣的第三方庫妇智。解決辦法就是把用到的第三方庫加上自定義前綴滥玷,包括類名、delegate 協(xié)議巍棱、常量名惑畴,尤其需要注意 Category 的方法名要修改。
5航徙、圖片等資源文件用 bundle 方式打包如贷。一個簡單制作 bundle 的方法:新建文件夾,重命名為 YourSDK.bundle捉偏,然后 Show Package Contents 打開倒得,加入圖片。使用圖片的時候需要指明 bundle: [UIImage imageNamed:@"YourSDK.bundle/img.png"]夭禽。也可以用 Target 方式制作 bundle霞掺,比如 iOS Library With Resourceshttp://www.galloway.me.uk/tutorials/ios-library-with-resources/.