iOS 制作靜態(tài)庫.a && 制作Framework

一、制作靜態(tài)庫.a文件

第一步

  • 創(chuàng)建一個新項(xiàng)目 選擇Cocoa Touch Static Library
    創(chuàng)建

第二步

  • Build Active Architecture Only 設(shè)置為NO(不同機(jī)型的架構(gòu)不一樣,設(shè)置為NO適配不同機(jī)型)
    設(shè)置NO

第三步

  • 跟平常一樣寫代碼 寫代碼的時候要注意命名


    寫代碼

第四步

  • 設(shè)置最低支持版本和暴露頭文件(別人能看到的.h文件)


    設(shè)置版本
頭文件

第五步

  • 運(yùn)行代碼生成對應(yīng)庫(模擬器和真機(jī)下分別在debug和release環(huán)境下運(yùn)行代碼[最后合并的時候注意對應(yīng)],總共是4次,右鍵點(diǎn)擊項(xiàng)目目錄里的庫.a文件,Show in Finder會發(fā)現(xiàn)4有個文件,對應(yīng)剛才4次運(yùn)行結(jié)果)
Show in finder

第六步

  • 合并庫文件(注意空格)

  • 說明:最終生成了兩個合并好的庫文件,debug和release。使用時根據(jù)當(dāng)前工程配置情況選用對應(yīng)庫文件。

  • 生成debug庫文件
    分別將模擬器和真機(jī)的兩個.a文件合并成一個.a文件 打開終端 lipo -create xxx/xxx/xx/xx.a xxx/xxx/xx/xx.a -output xxx/xx.a 前兩個xxx/xxx/xx/xx.a分別是模擬器和真機(jī)的.a文件的路徑 后面的是你要存放生成的.a文件的路徑 路徑一定要是.a文件(最后這里的庫名字是你自己寫在路徑里的,由你自己決定)

  • 終端:lipo -create debug下模擬器庫文件路徑 debug模式下真機(jī)庫文件路徑 -output 合并后庫文件路徑

  • 生成release庫文件
    終端:lipo -create release下模擬器庫文件路徑 release模式下真機(jī)庫文件路徑 -output 合并后庫文件路徑

合并

第七步

  • 使用!
  • 將對應(yīng)的合并好的.a文件添加到自己的工程中,看是否能正常使用。
  • 注意,制作的.a靜態(tài)庫是沒有.h的引用頭文件的,這里需要自己手動添加,在剛才的四個文件夾的include里,任選一個,添加至項(xiàng)目.
使用
使用成功

二、制作Framework文件

推薦參考

第一步

  • 創(chuàng)建一個新項(xiàng)目, Cocoa Touch Framework

第二步

  • Build Active Architecture Only 設(shè)置為NO(不同機(jī)型的架構(gòu)不一樣,設(shè)置為NO適配不同機(jī)型)

第三步

  • 加入自己的各種類文件,注意命名

第四步

  • 暴露頭文件
    注意:framework工程新建就有一個.h文件,其實(shí)就是一個主頭文件.我們在主頭文件中導(dǎo)入需要導(dǎo)入的頭文件,后面我們在使用這個靜態(tài)庫的時候只需要導(dǎo)入這個主頭文件即可.就像我們使用很多第三方開源框架一樣.
    圖四、和上圖不是一個項(xiàng)目了,這個不重要

第五步

  • Build Setting 搜索linking
    設(shè)置為靜態(tài)庫(默認(rèn)是動態(tài)庫), 將Mach-O Type設(shè)為Static Library,framework可以是動態(tài)庫也可以是靜態(tài)庫,對于系統(tǒng)的framework是動態(tài)庫,而用戶制作的framework只能是靜態(tài)庫.
    Link With Standard Libraries 設(shè)置為 NO(下圖漏了)
    設(shè)置Dead Code Stripping 為NO是編譯選項(xiàng)優(yōu)化,包瘦身(可不改)

第六步

  • 記得設(shè)置最低的支持版本

  • .a一樣,進(jìn)行command+B

    command+B

第七步

  • 合并:這里的合并指的是 1.debug 下真機(jī)+模擬器合并 2.release 下真機(jī)+模擬器合并
  • 注意:output文件后綴為.lipo
    生成的.lipo文件去掉后綴名,改為與合并前文件一樣的名稱,拖入開始運(yùn)行生成的人一個文件中,替換原來的.

lipo -create /Users/qujiahong/Library/Developer/Xcode/DerivedData/JHSomesLib-becdskpvrczmkueccmpfgkjviinr/Build/Products/Debug-iphonesimulator/JHSomesLib.framework/JHSomesLib /Users/qujiahong/Library/Developer/Xcode/DerivedData/JHSomesLib-becdskpvrczmkueccmpfgkjviinr/Build/Products/Debug-iphoneos/JHSomesLib.framework/JHSomesLib -output /Users/qujiahong/Desktop/ForPlugin/firstLib/JHSomesLib 


合并
  • 合并自己對應(yīng)環(huán)境下的,對應(yīng)使用即可

第八步

  • 使用!

  • 導(dǎo)入framework.


    使用

第九步、補(bǔ)充:這里還有一種自動合并的方法,利用腳本

  • 新建Aggregate Target(在當(dāng)前的這個工程下,點(diǎn)擊圖中的 + )
    新建Aggregate Target
創(chuàng)建一個Run Script腳本
  • 腳本植入代碼(推薦):
#!/bin/sh
#要build的target名
TARGET_NAME=${PROJECT_NAME}
if [[ $1 ]]
then
TARGET_NAME=$1
fi
UNIVERSAL_OUTPUT_FOLDER="${SRCROOT}/${PROJECT_NAME}/"

#創(chuàng)建輸出目錄,并刪除之前的framework文件
mkdir -p "${UNIVERSAL_OUTPUT_FOLDER}"
rm -rf "${UNIVERSAL_OUTPUT_FOLDER}/${TARGET_NAME}.framework"

#分別編譯模擬器和真機(jī)的Framework
xcodebuild -target "${TARGET_NAME}" ONLY_ACTIVE_ARCH=NO -configuration ${CONFIGURATION} -sdk iphoneos BUILD_DIR="${BUILD_DIR}" BUILD_ROOT="${BUILD_ROOT}" clean build
xcodebuild -target "${TARGET_NAME}" ONLY_ACTIVE_ARCH=NO -configuration ${CONFIGURATION} -sdk iphonesimulator BUILD_DIR="${BUILD_DIR}" BUILD_ROOT="${BUILD_ROOT}" clean build

#拷貝framework到univer目錄
cp -R "${BUILD_DIR}/${CONFIGURATION}-iphonesimulator/${TARGET_NAME}.framework" "${UNIVERSAL_OUTPUT_FOLDER}"

#合并framework,輸出最終的framework到build目錄
lipo -create -output "${UNIVERSAL_OUTPUT_FOLDER}/${TARGET_NAME}.framework/${TARGET_NAME}" "${BUILD_DIR}/${CONFIGURATION}-iphonesimulator/${TARGET_NAME}.framework/${TARGET_NAME}" "${BUILD_DIR}/${CONFIGURATION}-iphoneos/${TARGET_NAME}.framework/${TARGET_NAME}"

#刪除編譯之后生成的無關(guān)的配置文件
dir_path="${UNIVERSAL_OUTPUT_FOLDER}/${TARGET_NAME}.framework/"
for file in ls $dir_path
do
if [[ ${file} =~ ".xcconfig" ]]
then
rm -f "${dir_path}/${file}"
fi
done
#判斷build文件夾是否存在,存在則刪除
if [ -d "${SRCROOT}/build" ]
then
rm -rf "${SRCROOT}/build"
fi
rm -rf "${BUILD_DIR}/${CONFIGURATION}-iphonesimulator" "${BUILD_DIR}/${CONFIGURATION}-iphoneos"
#打開合并后的文件夾
open "${UNIVERSAL_OUTPUT_FOLDER}"

  • 或者這一段腳本(二選一)
if  [ "${ACTION}" = "build" ]

then

INSTALL_DIR=${SRCROOT}/Products/${PROJECT_NAME}.framework

DEVICE_DIR=${BUILD_ROOT}/${CONFIGURATION}-iphoneos/${PROJECT_NAME}.framework

SIMULATOR_DIR=${BUILD_ROOT}/${CONFIGURATION}-iphonesimulator/${PROJECT_NAME}.framework

if  [ -d "${INSTALL_DIR}" ]

then

rm -rf "${INSTALL_DIR}"

fi

mkdir -p "${INSTALL_DIR}"

cp -R "${DEVICE_DIR}/" "${INSTALL_DIR}/"

#ditto "${DEVICE_DIR}/Headers" "${INSTALL_DIR}/Headers"*

lipo -create "${DEVICE_DIR}/${PROJECT_NAME}" "${SIMULATOR_DIR}/${PROJECT_NAME}" -output "${INSTALL_DIR}/${PROJECT_NAME}"

open "${DEVICE_DIR}"

open "${SRCROOT}/Products"

fi

三、總結(jié)

1 、注意理解:無論是.a靜態(tài)庫還.framework靜態(tài)庫,我們需要的都是二進(jìn)制文件+.h+資源文件,不同的是,.a本身只是二進(jìn)制文件,需要配上.h和資源文件才能使用,而.framework本身已經(jīng)包含了二進(jìn)制文件、.h和資源文件,可以直接使用。

2 、圖片資源的處理:兩種靜態(tài)庫,一般都是把圖片文件單獨(dú)的放在一個.bundle文件中,一般.bundle的名字和.a或.framework的名字相同。新建一個文件夾,把它改名為.bundle,右鍵->顯示包內(nèi)容,之后就可以向其中添加資源文件。

3、 如果一個靜態(tài)庫很復(fù)雜,需要暴露的.h比較多的話,就可以在靜態(tài)庫的內(nèi)部創(chuàng)建一個.h文件(一般這個.h文件的名字和靜態(tài)庫的名字相同),然后把所有需要暴露出來的.h文件都集中放在這個.h文件中,而那些原本需要暴露的.h都不需要再暴露了,只需要把.h暴露出來就可以了。

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時請結(jié)合常識與多方信息審慎甄別。
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡書系信息發(fā)布平臺,僅提供信息存儲服務(wù)。

友情鏈接更多精彩內(nèi)容