ijk编译

iOS开发之ijkplayer的打包framework

920 发布: 2020/5/6 01:45 本文总阅读量

准备工作

安装homebrew, git, yasm.(如果已经安装好可以跳过, 不清楚的再来一遍也无妨,一般mac都已经安装)

ruby -e "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/master/install)"
brew install git
brew install yasm

ps:报错–>(Warning: /usr/local/bin is not in your PATH.)

终端输入命令: export PATH=/usr/local/bin:$PATH

获取 ijkplayer 源码

在一个合适的位置新建一个文件夹, 假设为桌面, 文件夹名为ijkplayer.

打开终端, 输入下面的指令

# 进入到刚刚新建的文件夹内
cd ~/Desktop/ijkplayer/

# 获取ijkplayer源码
git clone https://github.com/Bilibili/ijkplayer.git ijkplayer-ios

# 进入源码目录
cd ijkplayer-ios

# 切换分支 (目前为k0.8.8, 可以自行去GitHub查看最新版本号)
git checkout -B latest k0.8.8

配置编解码器格式支持

默认为最少支持, 如果足够你使用, 可以跳过这一步. 否则可以改为以下配置:

module-default.sh 更多的编解码器/格式
module-lite-hevc.sh 较少的编解码器/格式(包括hevc)
module-lite.sh较少的编解码器/格式(默认情况)

# 进入 config 目录
cd config

# 删除当前的 module.sh 文件
rm module.sh

# 可根据需要替换为`module-default.sh`, `module-lite-hevc.sh`, `module-lite.sh`
# 创建软链接 module.sh 指向 module-lite-hevc.sh
ln -s module-lite-hevc.sh module.sh

cd ..
cd ios
sh compile-ffmpeg.sh clean

获取 ffmpeg 并初始化

cd ..
./init-ios.sh

添加 https 支持

最后会生成支持https的静态文件libcrypto.alibssl.a,如果不需要可以跳过这一步

# 获取 openssl 并初始化
./init-ios-openssl.sh

cd ios

# 在模块文件中添加一行配置 以启用 openssl 组件
echo 'export COMMON_FF_CFG_FLAGS="$COMMON_FF_CFG_FLAGS --enable-openssl"' >> ../config/module.sh

./compile-ffmpeg.sh clean

编译

# 如果下一步提示错误`xcrun: error: SDK "iphoneos" cannot be located`, 请执行`sudo xcode-select --switch /Applications/Xcode.app/Contents/Developer/`, 再重新执行下一步

# 编译openssl, 如果不需要https可以跳过这一步
./compile-openssl.sh all

# 编译ffmpeg
./compile-ffmpeg.sh all

可能出现报错:

!! ERROR
!! Can not find FFmpeg directory for ffmpeg-armv7
!! Run 'sh init-ios.sh' first

解决:==>重新执行获取 ffmpeg 并初始化步骤

也有可能是这样错误:

./libavutil/arm/asm.S:50:9: error: unknown directive
        .arch armv7-a
        ^
make: *** [libavcodec/arm/aacpsdsp_neon.o] Error 1

最新的Xcode已经弱化了对 32 位的支持, 解决方法:
compile-ffmpeg.sh文件中删除armv7, 修改如:FF_ALL_ARCHS_IOS8_SDK="arm64 i386 x86_64" 再重新执行出现错误的命令:

 ./compile-ffmpeg.sh all

打开 IJKMediaPlayer 项目

用命令:

open IJKMediaPlayer/IJKMediaPlayer.xcodeproj

或者手动用 Xcode 打开 ios 目录下的 IJKMediaPlayer 项目.

添加 openssl 相关包以支持 https

如果不使用https, 可以跳过此步, 直接开始打包framwork 如果使用https, 那么需要手动给IJKMediaFramework添加libcrypto.alibssl.a文件, 默认不会添加

ps: 这两个依赖库的目录为:ijkplayer-ios/ios/build/universal/lib, 只有进行了上面跟openssl相关的操作, 才会在这个目录下有生成libcrypto.alibssl.a

项目1

打包 framwork

大家会发现除了IJKMediaFramework这个target, 还有一个叫IJKMediaFrameworkWithSSL, 但是不推荐使用这个, 因为大部分基于ijkplayer的第三方框架都是使用的前者, 你把后者导入项目还是会报找不到包的错误, 就算你要支持https也推荐使用前者, 然后按照上一步添加openssl即可支持

1.配置Release模式如果下图

项目2 项目3

2.打包真机framework 选择你连接的手机或者Generic iOS Device

项目4

如图操作,然后按键command+b编译即可

如果之前的步骤删除了compile-ffmpeg.sharmv7, 这里会报错, 我们直接注释掉就好(小伙伴仔细看啊,下面两张图不一样的)

项目5 项目6

具体路径
—-> /Users/你的用户名/Desktop/ijkplayer/ijkplayer-ios/ios/build/universal/include/libavutil/avconfig.h
—–> /Users/你的用户名/Desktop/ijkplayer/ijkplayer-ios/ios/build/universal/include/libffmpeg/config.h

具体文件路径这样查看
项目7

如图操作,然后command+b编译即可

3.打包模拟器framework 选择任意模拟器 然后command+b编译即可

4.合并framework

如果只需要真机运行或者模拟器运行, 可以不用合并, 直接找到对应的framework导入项目即可; 一般我们为了方便会合并 framework, 这样就同时支持模拟器和真机运行. 先找到生成framework的目录:

项目8 项目9

准备合并: 打开终端, 先cdProducts目录下 然后执行:lipo -create真机framework路径 模拟器framework路径 -output 合并的文件路径

lipo -create Release-iphoneos/IJKMediaFramework.framework/IJKMediaFramework Release-iphonesimulator/IJKMediaFramework.framework/IJKMediaFramework -output IJKMediaFramework

合并完成: 可以看到这里生成了一个大概两倍大小的文件, 将生成的IJKMediaFramework文件替换掉 真机framework中的 IJKMediaFramework文件,然后这个替换掉文件的 真机framework就是我们需要的 通用的framework了。

项目10 项目11

集成 framework 到项目中

·导入 framework

直接将IJKMediaFramework.framework拖入到工程中即可注意记得勾选Copy items if needed和 对应的target

· 添加下列依赖到工程

  1. libc++.tbd ( 编译器选 gcc 的请导入libstdc++.tbd)
  2. libz.tbd
  3. libbz2.tbd
  4. AudioToolbox.framework
  5. UIKit.framework
  6. CoreGraphics.framework
  7. AVFoundation.framework
  8. CoreMedia.framework
  9. CoreVideo.framework
  10. MediaPlayer.framework
  11. MobileCoreServices.framework
  12. OpenGLES.framework
  13. QuartzCore.framework
  14. VideoToolbox.framework

导入ijkplayer头文件运行一下项目, 如果遇到了类似这样的错误:

项目12

可能是因为导入的依赖库不全, 比如缺少libc++.tbd, 请再次对照添加好所有的依赖库:

项目13

简书参考地址地址

IJK使用扩展

创建IJKFFOptions,配置参数

    NSURL *url = [NSURL URLWithString:liveStreamString];

    [IJKFFMoviePlayerController checkIfFFmpegVersionMatch:YES];

    IJKFFOptions *options = [IJKFFOptions optionsByDefault];

    //设置Referer
    [options setOptionValue:@"key:value\r\n" forKey:@"headers" ofCategory:kIJKFFOptionCategoryFormat];

    //设置最大fps
    [options setPlayerOptionIntValue:30  forKey:@"max-fps"];

    //跳帧开关,如果cpu解码能力不足,可以设置成5,否则
    //会引起音视频不同步,也可以通过设置它来跳帧达到倍速播放
    [options setPlayerOptionIntValue:5  forKey:@"framedrop"];

    [options setCodecOptionIntValue:IJK_AVDISCARD_DEFAULT forKey:@"skip_frame"];

    //解码参数,画面更清晰
    [options setCodecOptionIntValue:IJK_AVDISCARD_DEFAULT forKey:@"skip_loop_filter"];

    //播放前的探测时间
    [options setFormatOptionIntValue:50000 forKey:@"analyzeduration"];

    //播放前的探测Size,默认是1M, 改小一点会出画面更快
    [options setFormatOptionIntValue:1024 * 16 forKey:@"probesize"];

    //如果是rtsp协议,可以优先用tcp(默认是用udp)
    //[options setFormatOptionValue:@"tcp" forKey:@"rtsp_transport"];

    //开启硬解码 1是硬解 0是软解
    [options setPlayerOptionIntValue:0  forKey:@"videotoolbox"];

    // 帧速率(fps) (可以改,确认非标准桢率会导致音画不同步,所以只能设定为15或者29.97)
    [options setPlayerOptionIntValue:29.97 forKey:@"r"];

    // -vol——设置音量大小,256为标准音量。(要设置成两倍音量时则输入512,依此类推
    //[options setPlayerOptionIntValue:512 forKey:@"vol"];

    //静音设置
    [options setPlayerOptionValue:@"1" forKey:@"an"];

    //帧数
    [options setPlayerOptionIntValue:5  forKey:@"min-frames"];
    
    //Param for living
    //最大缓存大小是3秒,可以依据自己的需求修改
    [options setPlayerOptionIntValue:3000 forKey:@"max_cached_duration"];

    //无限读
    [options setPlayerOptionIntValue:1 forKey:@"infbuf"];

    //关闭播放器缓冲初始化player的时候将option加入
    [options setPlayerOptionIntValue:0 forKey:@"packet-buffering"];  

    IJKFFMoviePlayerController *moviePlayer = [[IJKFFMoviePlayerController alloc] initWithContentURL:url withOptions:options];