有关ffmpeg的编译资料网上一大推,但是照着资料拷贝的运行进行编译能顺利编译出静态库或静态库产物的寥寥无几。
笔者在学习的时候也是踩了很多的坑,确实是每次编译会诞生一个放弃的念头,原因还是自己的基础学得不够扎实。
因为ffmpeg和NDK都是在不断进行迭代的,比如说NDK在r18之后之后彻底移除了gcc(包含r18版本),ffmpeg在4.o版本开始也针对Android平台的交叉编译默认使用clang编译,但是网上的很多资料都是使用gcc编译的。
所以如果要对照网上资料进行编译的话,保证NDK版本和ffmpeg版本甚至是编译环境工具都和作者的一样,这样会大大提高编译的成功率。
在编译成功之后再不断尝试修改参数结合搜索资料尝试,力求弄清楚每个参数的意义,做到触类旁通。
本次编译使用的是mac苹果电脑,使用的NDK版本是r20,ffmpeg是从官网下载的最新版4.2.2。
编译脚本
从ffmpeg官网下载好源码解压后,进入源码目录,新建shell脚本文件,比如build_ffmpeg.sh
脚本内容如下:
#!/bin/bash
# 将NDK的路径替换成你自己的NDK路径
NDK=/Users/liangchuanfei/Documents/Android/SDK/android-ndk-r20b
API=21
# arm aarch64 i686 x86_64
ARCH=arm
# 指定目标cpu的架构 armv7a aarch64 i686 x86_64
PLATFORM=armv7a
TARGET=$PLATFORM-linux-androideabi
# 设置工具链mac苹果电脑的是darwin-x86_64 而如果是linux的话则是linux-x86_64
TOOLCHAIN=$NDK/toolchains/llvm/prebuilt/darwin-x86_64/bin
# 设置编译产物的输出目录,这里表示在当前目录下新建Android_out目录
PREFIX=./Android_out/$PLATFORM
CFLAG="-D__ANDROID_API__=$API -U_FILE_OFFSET_BITS -DBIONIC_IOCTL_NO_SIGNEDNESS_OVERLOAD -Os -fPIC -DANDROID -D__thumb__ -mthumb -Wfatal-errors -Wno-deprecated -mfloat-abi=softfp -marm"
build_one()
{
#执行configure脚本,用于生成makefile
./configure \
--ln_s="cp -rf" \
--prefix=$PREFIX \
# 指定交叉编译工具
--cc=$TOOLCHAIN/$TARGET$API-clang \
--cxx=$TOOLCHAIN/$TARGET$API-clang++ \
--ld=$TOOLCHAIN/$TARGET$API-clang \
# 设置android目标平台之后编译出来的动态库不带版本号,方便JNI调用
--target-os=android \
--arch=$ARCH \
--cpu=$PLATFORM \
--cross-prefix=$TOOLCHAIN/$ARCH-linux-androideabi- \
# 开启交叉编译
--enable-cross-compile \
--enable-shared \
--disable-static \
--enable-runtime-cpudetect \
--disable-doc \
--disable-ffmpeg \
--disable-ffplay \
--disable-ffprobe \
--disable-doc \
--disable-symver \
# 优化大小
--enable-small \
--enable-gpl \
--enable-nonfree \
--enable-version3 \
--disable-iconv \
--enable-neon \
--enable-hwaccels \
--enable-jni \
--enable-mediacodec \
# 关闭avdevice模块,此模块在android中无用
--disable-avdevice \
--disable-decoders \
--enable-decoder=vp9 \
--enable-decoder=h264 \
--enable-decoder=mpeg4 \
--enable-decoder=aac \
--enable-decoder=h264_mediacodec \
--disable-postproc \
# 会传给编译器的参数
--extra-cflags="$CFLAG" \
--extra-ldflags="-marm"
}
build_one
make clean
# 使用4条线程进行编译,增加编译速度
make -j4
make install
保存后运行脚本./build_ffmpeg.sh
。
运行脚本的时候可能会遇到没有权限的问题,运行命令行chmod +x build_ffmpeg.sh
增加一下执行权限后再次执行即可进行编译。
如果没有报错,大概几分钟后就能看编译成功:
编译成功后在目标输出目录下会生成三个文件,如图:
其中include
目录下是使用动态库或静态库时所需要的一些头文件; lib
目录存放着编译产物动态库或者静态库;share
目录则存放一些简单的demo,我们可以参照这些demo编写音视频的编解码等逻辑。
一些技巧
更多参数可在ffmpeg的源码目录下执行./configure --help
查看。
CFLAG参数这么长,怎么来的?其实这个不用死记,可以从AS NDK工程的.externativeBuild/cmake/debug/armeabi-v7a/build.ninja中拷贝,需要注意的是替换掉NDK的路径地址。
与网上gcc编译的脚本对比可以发现少了一些类似--sysroot
这样的参数,或许这就是clang的好处之一吧。
最后如果你对音视频开发感兴趣可扫码关注,后续我们共同探讨,共同进步。
本文来自作者投稿,版权归原作者所有。如需转载,请注明出处:https://www.nxrte.com/jishu/19835.html