ios-cmake 生成framework并在Headers/保留項(xiàng)目目錄結(jié)構(gòu)

前言

公司有個(gè)C/C++/ObjC的底層算法庫(kù)需要在IOS上使用,做了一番調(diào)查之后決定將其編成framework的形式(至于IOS上靜態(tài)庫(kù)后频、動(dòng)態(tài)庫(kù)和framework的區(qū)別沼撕,網(wǎng)上已經(jīng)有很多文章了遭顶,這里就不再累述了)。

提醒:底下的大部分鏈接都需要翻墻訪問(wèn)牛柒。

正文

ios-cmake生成framework

由于項(xiàng)目一直是用CMake來(lái)管理堪簿,所以找到了ios-cmake生成framework的方法,在Github上就有:用cmake生成ios framework庫(kù)皮壁。我使用的是其中的第二種方法椭更,也就是使用這里的ios.toolchain.cmake進(jìn)行編譯。

其中困擾了很久的問(wèn)題就是如何在framework/Headers中保留原有項(xiàng)目的目錄結(jié)構(gòu)蛾魄,找了很久虑瀑,提出這個(gè)問(wèn)題的人不少湿滓,但解決方案不合適,比如這里的:iOS框架標(biāo)題不保留文件夾層次結(jié)構(gòu)舌狗。
一開(kāi)始我采用了shell腳本手動(dòng)移動(dòng)文件的方法來(lái)達(dá)成需求叽奥,但這樣對(duì)于一個(gè)大型項(xiàng)目來(lái)說(shuō)顯然是很low的,一旦文件目錄更改痛侍,就得同時(shí)修改CMakeLists.txt和shell腳本朝氓,改的越多,出錯(cuò)就越容易主届。所以還是得找到一個(gè)可以在CMake里面實(shí)現(xiàn)的方法赵哲,最終被我找到了,如果急著解決君丁,可以看這里:一個(gè)2010年的帖子枫夺。不著急的話,就看一下我在底下寫(xiě)的一個(gè)小例子吧谈截。

項(xiàng)目結(jié)構(gòu)和初步的CMakeLists.txt

如圖所示筷屡,源文件和頭文件按功能模塊分目錄涧偷,都在src底下簸喂,src/CMakeLists.txt負(fù)責(zé)編譯這些文件,頂層目錄有三個(gè)文件:

  • build.sh: 編譯用的腳本
  • CMakeLists.txt:頂層CMakeLists.txt燎潮,可以用來(lái)編譯外部的文件喻鳄,這里只用來(lái)add_subdirectory(src)
  • ios.toolchain.cmake:直接從上面所說(shuō)的網(wǎng)址上clone下來(lái)的
在這里插入圖片描述

src/CMakeLists.txt

主要部分是“用cmake生成ios framework庫(kù)”這里提到的,而在framework/Headers保留目錄結(jié)構(gòu)的關(guān)鍵則是:MACOSX_PACKAGE_LOCATION

src/CMakeLists.txt內(nèi)容如下所示确封,備注應(yīng)該挺清楚的了的吧除呵。

cmake_minimum_required(VERSION 3.0)
set(CMAKE_CXX_STANDARD 11)

# 在這里所指示的目錄將會(huì)成為最終framework/Headers底下的目錄
set(dir1 dir1/test.cc dir1/test.h)
set(dir1_ios dir1/ios/test_ios.cc dir1/ios/test_ios.h)
set(dir2_1 dir2/subDir1/test2.cc dir2/subDir1/test2.h)
set(dir2_2 dir2/subDir2/test3.cc dir2/subDir2/test3.h)
set(dir3 dir3/test.cc dir3/test.h)

add_library(testFramework
    ${dir1}
    ${dir1_ios}
    ${dir2_1}
    ${dir2_2}
    ${dir3}
    )  

# 這里鏈接了第三方庫(kù):opencv.framework和幾個(gè)系統(tǒng)庫(kù)
set_target_properties(testFramework PROPERTIES
    #-F后面接著的是opencv2.framework所在目錄
    LINK_FLAGS "-W1,-F${CMAKE_CURRENT_SOURCE_DIR}/3party/opencv/ios"
    )
target_link_libraries(testFramework 
        "-framework opencv2"
        "-framework Foundation" 
        "-framework CoreVideo"
        "-framework coreml"
        )

# 列出要編譯的所有源文件和頭文件
set(SRC_FILES
    ${dir1}
    ${dir1_ios}
    ${dir2_1}
    ${dir2_2}
    ${dir3}
    )

# 從SRC_FILES列表中找出所有頭文件,并放入INCLUDE_FILES變量中
set(INCLUDE_FILES "")
foreach(file ${SRC_FILES})
    # 通過(guò)識(shí)別".h"子字符串的方式得出一個(gè)文件是否是頭文件爪喘,所以.h和.hpp文件都會(huì)被找到
    string(FIND ${file} ".h" pos REVERSE)  
    if(NOT ${pos} MATCHES "-1")
        message(STATUS "header file: ${file}")
        list(APPEND INCLUDE_FILES ${file})
    endif()
endforeach(file)
set(INCLUDE_FILES ${INCLUDE_FILES} CACHE INTERNAL "List of include files" FORCE)

set_xcode_property(testFramework GCC_GENERATE_DEBUGGING_SYMBOLS YES "ALL")
set_target_properties(testFramework PROPERTIES
    FRAMEWORK TRUE
    FRAMEWORK_VERSION A
    MACOSX_FRAMEWORK_IDENTIFIER cn.yrh.test
    VERSION 1.0.0
    SOVERSION 1.0.0
    #PUBLIC_HEADER ${INCLUDE_FILES} # 使用另一種方法生成Headers/颜曾,所以PUBLIC_HEADER就不用了
    )

# 將INCLUDE_FILES變量中的所有文件按其路徑名放入testFramework.framework/Headers中
foreach(hfile ${INCLUDE_FILES})
    # 截取出hfile變量中的路徑
    string(FIND ${hfile} "/" pos REVERSE)  # 得出最后一個(gè)"/"的位置pos
    string(SUBSTRING ${hfile} 0 ${pos} dir)
    message(STATUS "subDir: ${dir}")
    # MACOSX_PACKAGE_LOCATION關(guān)鍵字可以將文件復(fù)制到特定的路徑中,在IOS framework中秉剑,
    # 就是<name>.framework/
    set_property(SOURCE ${hfile} PROPERTY 
                MACOSX_PACKAGE_LOCATION Headers/${dir})
endforeach(hfile)

include_directories(
    .
    ${CMAKE_CURRENT_SOURCE_DIR}/3party/opencv/ios/opencv2.framework
    )

build.sh

#!/bin/bash
rm -r build-ios
mkdir build-ios
cd build-ios
cmake .. -G Xcode -DCMAKE_TOOLCHAIN_FILE=../ios.toolchain.cmake -DPLATFORM=OS64 -DARCHS=arm64 -DDEPLOYMENT_TARGET=12.2 -DENABLE_STRICT_TRY_COMPILE=TRUE -DENABLE_VISIBILITY=TRUE -DCMAKE_XCODE_ATTRIBUTE_DEVELOPMENT_TEAM=UBX9CH9GDX
cmake --build . --config Debug
#cmake --build . --config Release

解釋:最終編譯出來(lái)的文件都在build-ios目錄下泛豪,cmake的編譯選項(xiàng)在leetal/ios-cmake中有詳細(xì)介紹。
最終生成的framework應(yīng)該是在Debug-iphoneos或Release-iphoneos目錄下侦鹏。

對(duì)了诡曙,這個(gè)也是我:


yeRuiHuan
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個(gè)濱河市略水,隨后出現(xiàn)的幾起案子价卤,更是在濱河造成了極大的恐慌,老刑警劉巖渊涝,帶你破解...
    沈念sama閱讀 221,888評(píng)論 6 515
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件慎璧,死亡現(xiàn)場(chǎng)離奇詭異床嫌,居然都是意外死亡,警方通過(guò)查閱死者的電腦和手機(jī)胸私,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 94,677評(píng)論 3 399
  • 文/潘曉璐 我一進(jìn)店門(mén)既鞠,熙熙樓的掌柜王于貴愁眉苦臉地迎上來(lái),“玉大人盖文,你說(shuō)我怎么就攤上這事嘱蛋。” “怎么了五续?”我有些...
    開(kāi)封第一講書(shū)人閱讀 168,386評(píng)論 0 360
  • 文/不壞的土叔 我叫張陵洒敏,是天一觀的道長(zhǎng)。 經(jīng)常有香客問(wèn)我疙驾,道長(zhǎng)凶伙,這世上最難降的妖魔是什么? 我笑而不...
    開(kāi)封第一講書(shū)人閱讀 59,726評(píng)論 1 297
  • 正文 為了忘掉前任它碎,我火速辦了婚禮函荣,結(jié)果婚禮上,老公的妹妹穿的比我還像新娘扳肛。我一直安慰自己傻挂,他們只是感情好,可當(dāng)我...
    茶點(diǎn)故事閱讀 68,729評(píng)論 6 397
  • 文/花漫 我一把揭開(kāi)白布挖息。 她就那樣靜靜地躺著金拒,像睡著了一般。 火紅的嫁衣襯著肌膚如雪套腹。 梳的紋絲不亂的頭發(fā)上绪抛,一...
    開(kāi)封第一講書(shū)人閱讀 52,337評(píng)論 1 310
  • 那天,我揣著相機(jī)與錄音电禀,去河邊找鬼幢码。 笑死,一個(gè)胖子當(dāng)著我的面吹牛尖飞,可吹牛的內(nèi)容都是我干的症副。 我是一名探鬼主播,決...
    沈念sama閱讀 40,902評(píng)論 3 421
  • 文/蒼蘭香墨 我猛地睜開(kāi)眼葫松,長(zhǎng)吁一口氣:“原來(lái)是場(chǎng)噩夢(mèng)啊……” “哼瓦糕!你這毒婦竟也來(lái)了?” 一聲冷哼從身側(cè)響起腋么,我...
    開(kāi)封第一講書(shū)人閱讀 39,807評(píng)論 0 276
  • 序言:老撾萬(wàn)榮一對(duì)情侶失蹤咕娄,失蹤者是張志新(化名)和其女友劉穎,沒(méi)想到半個(gè)月后珊擂,有當(dāng)?shù)厝嗽跇?shù)林里發(fā)現(xiàn)了一具尸體圣勒,經(jīng)...
    沈念sama閱讀 46,349評(píng)論 1 318
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡费变,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 38,439評(píng)論 3 340
  • 正文 我和宋清朗相戀三年,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了圣贸。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片挚歧。...
    茶點(diǎn)故事閱讀 40,567評(píng)論 1 352
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡,死狀恐怖吁峻,靈堂內(nèi)的尸體忽然破棺而出滑负,到底是詐尸還是另有隱情,我是刑警寧澤用含,帶...
    沈念sama閱讀 36,242評(píng)論 5 350
  • 正文 年R本政府宣布矮慕,位于F島的核電站,受9級(jí)特大地震影響啄骇,放射性物質(zhì)發(fā)生泄漏痴鳄。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,933評(píng)論 3 334
  • 文/蒙蒙 一缸夹、第九天 我趴在偏房一處隱蔽的房頂上張望痪寻。 院中可真熱鬧,春花似錦虽惭、人聲如沸橡类。這莊子的主人今日做“春日...
    開(kāi)封第一講書(shū)人閱讀 32,420評(píng)論 0 24
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽(yáng)猫态。三九已至,卻和暖如春披摄,著一層夾襖步出監(jiān)牢的瞬間,已是汗流浹背勇凭。 一陣腳步聲響...
    開(kāi)封第一講書(shū)人閱讀 33,531評(píng)論 1 272
  • 我被黑心中介騙來(lái)泰國(guó)打工疚膊, 沒(méi)想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留,地道東北人虾标。 一個(gè)月前我還...
    沈念sama閱讀 48,995評(píng)論 3 377
  • 正文 我出身青樓寓盗,卻偏偏與公主長(zhǎng)得像,于是被迫代替她去往敵國(guó)和親璧函。 傳聞我的和親對(duì)象是個(gè)殘疾皇子傀蚌,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 45,585評(píng)論 2 359

推薦閱讀更多精彩內(nèi)容