iOS Framework那些事儿

来源:互联网 发布:哪里的mac pro最便宜 编辑:程序博客网 时间:2024/05/16 08:28
iOS Framework那些事儿
        各大公司各种开源来袭,各种iOS SDK也相继出来了,国外各种开源框架在中国发挥淋漓尽致,所以相就出现了不同Framework引用同一第三方开源代码,造成各种使用问题,今天以SBJSON为例来讲讲iOS Framework,讲讲iOS Framework的那些事。
        本文主要参考:kstenerud / iOS-Universal-Framework  

一。iOS Framework的类型

1. Dynamically Linked Framework(动态连接库)  苹果安装在iOS 设备上的Framework,如我们经常使用的:Foundation.framework,UIKit.framework

2.Statically Linked Framework
 (静态连接库)  在编译时连接,所以这些很少出问题,哪微信SDK.a,二维码扫描库ZBarSDK libzbar.a

3.Fake Framework(虚拟的库)    通过使用一些脚本文件让xcode 读取bundle资源,看上去是一个静态库,在大部分功能上表现和一个真实Framework 工程一样。本质是一个Bundle(打包了第三方库SBJSON)

4.Real Framework(真实的库)  同Fake Framework ,但是不打包第三方库,使用者要自己引用第三方库。
本质是一个Bundle(没有打包
第三方库SBJSON)

二 。创建iOS Framework

1. 
Dynamically Linked Framework(动态连接库) 
    无法创建,苹果在系统级别预装
2. 
Statically Linked Framework
 (静态连接库) 
     可以使用Xcode自带的模板生成Xcode->File->New->Project->Cocoa Touch Static Library
    以
iOSStaticLib为例 
图片

分别用iphonesimulator 与 iphoneos 编译会生成两个libiOSStaticLib.a,为了全同一个.a能同时在模拟器与真上使用,可以使用命令行工具
lipo

如:
lipo -create Release-iphoneos/libiOSStaticLib.a Release-iphonesimulator/libiOSStaticLib.a -o libiOSStaticLib_universal.a 
图片 

把生成的 
libiOSStaticLib_universal.a  与 include下的头文件 放入工程,模拟器与真机可以使用

为了方便写了一个脚本方便直接生成 
 libiOSStaticLib_universal.a 与头文件

下载地址:Google协作平台buildLib.sh 

#!/bin/bash

PROJNAME=iOSStaticLib

BUILD_DIR=build

HEADERDIR=$BUILD_DIR/Header

LIBDIR="$BUILD_DIR/$PROJNAME.lib"

#ready Director

readyDirs()

{

/bin/rm -Rf $BUILD_DIR

/bin/mkdir $BUILD_DIR

/bin/mkdir $HEADERDIR

}

#xcode build lib

buildLib()

{

# build device

xcodebuild -project iOSStaticLib.xcodeproj -target iOSStaticLib -configuration Release -sdk iphoneos6.0

#build simulator

xcodebuild -project iOSStaticLib.xcodeproj -target iOSStaticLib -configuration Release -sdk iphonesimulator6.0

}


#copy open header file

copyOpenHeaders()

{

/bin/cp $PROJNAME/*.h $HEADERDIR/

}

# name and build location

createStaticLib()

{

# Clean any existing framework that might be there

if [ -d "$LIBDIR" ]

then

rm -rf "$LIBDIR"

fi

mkdir -p $LIBDIR

mkdir -p $LIBDIR/Headers

cp -R ${HEADERDIR}/* $LIBDIR/Headers/

#universal

lipo -create $BUILD_DIR/Release-iphoneos/libiOSStaticLib.a $BUILD_DIR/Release-iphonesimulator/libiOSStaticLib.a -o $LIBDIR/$PROJNAME

#zip

/usr/bin/zip -r $LIBDIR.zip $LIBDIR

}

#ready

readyDirs

#build

buildLib

#copy

copyOpenHeaders

#framework

createStaticLib

3.Fake Framework(虚拟的库) 
 所谓的framework 就是static lib + 资源生成的Bundle,所以Fake Framework是使用上面生成的libiOSStaticLib_universal.a 组织成一定结构的文件夹
iOS Framework的文件结构与命名规范为:
图片

libiOSStaticLib.framework 目录:
a.Headers 是对外开放的*.h头文件  
b. 
libiOSStaticLib 为上面生成的 libiOSStaticLib_universal.a二进制文件
c.Resources 资源文件


把libiOSStaticLib.framework 添加到工程就可以使用,为了方便使用写了一个脚本

下载地址:Google协作平台buildFakeFramework.sh 

#!/bin/bash
#
 
# prepare build directories

#

PROJNAME=iOSStaticLib

BUILD_DIR=build

HEADERDIR=$BUILD_DIR/Header

FRAMEWORKDIR="$BUILD_DIR/$PROJNAME.Framework"

#ready Director

readyDirs()

{

    /bin/rm -Rf $BUILD_DIR

     /bin/mkdir $BUILD_DIR

    /bin/mkdir $HEADERDIR

}

#xcode build lib

buildLib()

{

    # build device

    xcodebuild -project iOSStaticLib.xcodeproj -target iOSStaticLib -configuration Release -sdk iphoneos6.0

    #build simulator

    xcodebuild -project iOSStaticLib.xcodeproj -target iOSStaticLib -configuration Release -sdk iphonesimulator6.0

}

#copy open header file

copyOpenHeaders()

{

    /bin/cp $PROJNAME/*.h $HEADERDIR/

}

#

# create framework

#

# name and build location

createFramework()

{

    # Clean any existing framework that might be there

    if [ -d "$FRAMEWORKDIR" ]

    then

    rm -rf "$FRAMEWORKDIR"

    fi

    mkdir -p $FRAMEWORKDIR

    mkdir -p $FRAMEWORKDIR/Resources

    mkdir -p $FRAMEWORKDIR/Headers

    cp -R ${HEADERDIR}/* $FRAMEWORKDIR/Headers/

   #universal

    lipo -create $BUILD_DIR/Release-iphoneos/libiOSStaticLib.a $BUILD_DIR/Release-iphonesimulator/libiOSStaticLib.a -o $FRAMEWORKDIR/$PROJNAME

    #zip

    /usr/bin/zip -r $FRAMEWORKDIR.zip $FRAMEWORKDIR

}

#ready

readyDirs

#build

buildLib

#copy

copyOpenHeaders

#framework

createFramework


4.Real Framework(真实的库) 同Fake Framework 但是只是概念与设置不同 

这里要讲以SBJSON为例来讲Fake 与 Real的区别

Fake 模式下引用SBJSON会把SBJSON 源码
SBJSON.m SBJsonBase.m SBJsonParser.m SBJsonWriter.m编译到二进制包里面
引用工程不在需要引用SBJSON源码

Real 模式下 
 引用SBJSON会编译SBJSON.m SBJsonBase.m SBJsonParser.m SBJsonWriter.m源码文件到二进制包里面,引用工程需要添加SBJSON源码到工程,这样要保证工程中的SBJSON源码能兼容Real Framework(引用一个同事的话,如果不兼容说明SBJSON不够强大,可以考虑不在使用,选择其它兼容性强的开源代码)


在Xcode中的设置是TARGET的Build Phases -> Compile Sources 

Fake 设置为:
图片 

添加
SBJSON.m SBJsonBase.m SBJsonParser.m SBJsonWriter.m源码文件,会编译链接生成二进制文件,用BBEdit查看编译后的二进制文件搜索 SBJsonWriter.m 结果为:
图片 

可以搜索到SBJsonWriter.m 字符串,说明编译了SBJsonWriter.m文件

Real 设置为:
图片 

不添加SBJSON.m SBJsonBase.m SBJsonParser.m SBJsonWriter.m,也就framework工程不编译这些文件,只是引用,用BBEdit查看编译后的二进制文件搜索 SBJsonWriter.m 结果为:
搜索提示,找不到相应字符串,说明没有编译
SBJsonWriter.m文件,引用工程一定添加SBJsonWriter.m,不然工程提示找不到SBJsonWriter定义
 
图片


三。注意问题

1.在Framework工程里面不能创建基础类的Category,没有类符号找不到方法,直接Crash

2.如果是Real 方式的Framework 一定要选择兼容性强的第三方开源代码,并列出所以Framework使用的开源代码

四。所有使用源码

Google协作平台Zip下载

五。有问题可以空间留言,评论
原创粉丝点击