android ffmegp for_编译FFmpeg for Android,并增加x264支持

准备环节:

编译环境为Linux,笔者用的是Ubuntu16.04;

确保NDK环境配置可用;

需要的环境和文件准备好了之后,就可以开始准备编译咯

为了让编译得到的库能适合Android,需要修改配置文件ffmpeg/configure

#SLIBNAME_WITH_MAJOR='$(SLIBNAME).$(LIBMAJOR)'

SLIBNAME_WITH_MAJOR='$(SLIBPREF)$(FULLNAME)-$(LIBMAJOR)$(SLIBSUF)'

#LIB_INSTALL_EXTRA_CMD='$$(RANLIB) "$(LIBDIR)/$(LIBNAME)"'

LIB_INSTALL_EXTRA_CMD='$$(RANLIB)"$(LIBDIR)/$(LIBNAME)"'

#SLIB_INSTALL_NAME='$(SLIBNAME_WITH_VERSION)'

SLIB_INSTALL_NAME='$(SLIBNAME_WITH_MAJOR)'

#SLIB_INSTALL_LINKS='$(SLIBNAME_WITH_MAJOR) $(SLIBNAME)'

SLIB_INSTALL_LINKS='$(SLIBNAME)'

在jni目录下面创建一个文件build_ffmpeg_with_x264.sh,用于配置环境变量和控制编译主流程;

在x264目录下面创建一个文件build_x264_for_android.sh,用于编译x264;

在ffmpeg目录下面创建一个文件build_ffmpeg_for_android.sh,用于编译ffmpeg;

这样就可以编译出ffmpeg的库,如果在编译时提醒需要什么工具,直接安装完之后再重新执行脚本。

上面说到三个文件现在来逐一解析一下。

首先,看看build_ffmpeg_with_x264.sh,从文件名可以看出,该脚本就是把ffmpeg和x264混合编译。

#!/bin/bash

#配置NDK路径

export NDK=/opt/Sdk/ndk-bundle

# 检测NDK

if [[ -z "$NDK" ]]; then

echo "The NDK dir is empty, If the shell can not run normally, you should set the NDK variable to your local ndk.dir"

exit 1

fi

# 检测系统

OS=`uname`

HOST_ARCH=`uname -m`

export CCACHE=; type ccache >/dev/null 2>&1 && export CCACHE=ccache

if [ $OS == 'Linux' ]; then

export HOST_SYSTEM=linux-$HOST_ARCH

elif [ $OS == 'Darwin' ]; then

export HOST_SYSTEM=darwin-$HOST_ARCH

fi

# 配置 SYSROOT 和 CROSS_PREFIX,基于android-15

SYSROOT=$NDK/platforms/android-15/arch-arm

CROSS_PREFIX=$NDK/toolchains/arm-linux-androideabi-4.9/prebuilt/$HOST_SYSTEM/bin/arm-linux-androideabi-

echo "CROSS_PREFIX=$CROSS_PREFIX"

ROOT_DIR=`pwd`/

COMMOND_DIR=command_source

echo $ROOT_DIR

#配置输出路径

PREFIX=$ROOT_DIR/build

if [[ ! -d "$PREFIX" ]]; then

mkdir $PREFIX

fi

#### 编译步骤 开始 ####

#1、编译x264

#2、编译ffmpeg

#3、ndk-build

#### 编译步骤 结束 ####

#预先编译x264,编译类型为静态库#

X264_SOURCE_DIR=x264

if [[ ! -d "$X264_SOURCE_DIR" ]]; then

git clone http://git.videolan.org/git/x264.git $X264_SOURCE_DIR

fi

cp $ROOT_DIR$COMMOND_DIR/build_x264_for_android.sh $X264_SOURCE_DIR/build_x264_for_android.sh

TARGET_X264_DIR=$ROOT_DIR$X264_SOURCE_DIR

source $X264_SOURCE_DIR/build_x264_for_android.sh

#编译ffmpeg,编译为多个静态库#

FFMPEG_SOURCE_DIR=ffmpeg-3.3

if [[ ! -d "$FFMPEG_SOURCE_DIR" ]]; then

git clone git://source.ffmpeg.org/ffmpeg.git $FFMPEG_SOURCE_DIR

fi

cp $ROOT_DIR$COMMOND_DIR/build_for_android.sh $FFMPEG_SOURCE_DIR/build_for_android.sh

TARGET_FFMPEG_DIR=$ROOT_DIR$FFMPEG_SOURCE_DIR

source $FFMPEG_SOURCE_DIR/build_ffmpeg_for_android.sh

#执行ndk-build

$NDK/ndk-build

build_x264_for_android.sh文件内容如下:

#!/bin/bash

echo "###### 开始编译 x264 ######"

SOURCE=$TARGET_X264_DIR

echo $SOURCE

cd $SOURCE

EXTRA_CFLAGS="-march=armv7-a -mfloat-abi=softfp -mfpu=neon -D__ARM_ARCH_7__ -D__ARM_ARCH_7A__"

EXTRA_LDFLAGS="-nostdlib"

./configure \

配置输出路径

--prefix=$PREFIX \

配置交叉编译路径前缀

--cross-prefix=$CROSS_PREFIX \

--extra-cflags="$EXTRA_CFLAGS" \

--extra-ldflags="$EXTRA_LDFLAGS" \

--enable-static \

--enable-pic \

--enable-strip \

--disable-cli \

--host=arm-linux \

--sysroot=$SYSROOT

make clean

make && make install

echo "###### x264编译完成 ######"

cd ../

运行前需要把上面的两行中文注释删除,因为configure中间不能有注释,所以我就直接没有加#来注释,便于发现问题。

build_ffmpeg_for_android.sh文件内容如下:

#!/bin/bash

echo "###### 开始编译 ffmpeg ######"

SOURCE=$TARGET_FFMPEG_DIR

echo $SOURCE

cd $SOURCE

ADD_H264_FEATURE="--enable-encoder=aac \

--enable-decoder=aac \

--enable-gpl \

--enable-encoder=libx264 \

--enable-libx264 \

--extra-cflags=-I$PREFIX/include \

--extra-ldflags=-L$PREFIX/lib "

function build_one_so

{

./configure \

--prefix=$PREFIX \

--disable-shared \

--enable-pthreads \

--enable-gpl \

--enable-version3 \

--enable-nonfree \

--enable-static \

--enable-ffmpeg \

--disable-ffplay \

--disable-ffprobe \

--disable-ffserver \

--disable-doc \

--disable-symver \

--enable-avdevice \

--enable-avfilter \

--enable-libx264 \

--enable-small \

--enable-asm \

--enable-neon \

--cross-prefix=$CROSS_PREFIX \

--target-os=linux \

--arch=arm \

--enable-cross-compile \

--enable-runtime-cpudetect \

--sysroot=$SYSROOT \

--disable-parsers \

--enable-parser=aac \

--enable-parser=h264 \

--enable-parser=mjpeg \

--enable-parser=png \

--enable-parser=bmp \

--enable-parser=mpegvideo \

--enable-parser=mpegaudio \

--disable-encoders \

--enable-encoder=h263 \

--enable-encoder=libx264 \

--enable-encoder=mpeg4 \

--enable-encoder=aac \

--enable-encoder=png \

--enable-encoder=gif \

--enable-encoder=bmp \

--disable-decoders \

--enable-decoder=h263 \

--enable-decoder=h264 \

--enable-decoder=mpeg4 \

--enable-decoder=mjpeg \

--enable-decoder=gif \

--enable-decoder=mp3 \

--enable-decoder=aac \

--enable-decoder=png \

--enable-decoder=bmp \

--enable-decoder=yuv4 \

--disable-network \

--enable-protocols \

--enable-protocol=concat \

--enable-protocol=hls \

--enable-protocol=file \

--disable-demuxers \

--enable-demuxer=h263 \

--enable-demuxer=h264 \

--enable-demuxer=flv \

--enable-demuxer=gif \

--enable-demuxer=aac \

--enable-demuxer=ogg \

--enable-demuxer=dts \

--enable-demuxer=mp3 \

--enable-demuxer=mov \

--enable-demuxer=m4v \

--enable-demuxer=concat \

--enable-demuxer=mpegts \

--enable-demuxer=mjpeg \

--enable-demuxer=mpegvideo \

--enable-demuxer=rawvideo \

--enable-demuxer=yuv4mpegpipe \

--disable-muxers \

--enable-muxer=h264 \

--enable-muxer=flv \

--enable-muxer=gif \

--enable-muxer=mp3 \

--enable-muxer=dts \

--enable-muxer=mp4 \

--enable-muxer=mov \

--enable-muxer=mpegts \

--disable-filters \

--enable-filter=aresample \

--enable-filter=asetpts \

--enable-filter=setpts \

--enable-filter=ass \

--enable-filter=scale \

--enable-filter=concat \

--enable-filter=atempo \

--enable-filter=movie \

--enable-filter=overlay \

--enable-filter=rotate \

--enable-filter=transpose \

--enable-filter=hflip \

--extra-cflags="-mfloat-abi=softfp -mfpu=neon -marm -march=armv7-a" \

$ADD_H264_FEATURE

make clean

make -j4

make install

}

build_one_so

echo "###### ffmpeg编译完成 ######"

cd ../

这个脚本稍微多一点,主要是对ffmpeg的定制,由于ffmpeg全部功能打开的话,最终生成的库会很大,通常我们需要根据需求,对ffmpeg进行定制裁剪,根据encoder,decoder,muxer,demuxer,parser,filter,protocol等七个方面进行。首先都会全部disable,然后根据需求再enable需要的格式和功能。

上面是编译ffmpeg需要的配置,为了编译出Android可用的so文件,还需要配置Android.mk文件

LOCAL_PATH := $(call my-dir)

#include $(call all-subdir-makefiles)

#static version of libavcodec

include $(CLEAR_VARS)

LOCAL_MODULE:= libavcodec_static

LOCAL_SRC_FILES:= ./build/lib/libavcodec.a

LOCAL_EXPORT_C_INCLUDES := $(LOCAL_PATH)

include $(PREBUILT_STATIC_LIBRARY)

#static version of libavformat

include $(CLEAR_VARS)

LOCAL_MODULE:= libavformat_static

LOCAL_SRC_FILES:= ./build/lib/libavformat.a

LOCAL_EXPORT_C_INCLUDES := $(LOCAL_PATH)

include $(PREBUILT_STATIC_LIBRARY)

#static version of libswscale

include $(CLEAR_VARS)

LOCAL_MODULE:= libswscale_static

LOCAL_SRC_FILES:= ./build/lib/libswscale.a

LOCAL_EXPORT_C_INCLUDES := $(LOCAL_PATH)

include $(PREBUILT_STATIC_LIBRARY)

#static version of libavutil

include $(CLEAR_VARS)

LOCAL_MODULE:= libavutil_static

LOCAL_SRC_FILES:= ./build/lib/libavutil.a

LOCAL_EXPORT_C_INCLUDES := $(LOCAL_PATH)

include $(PREBUILT_STATIC_LIBRARY)

#static version of libavdevice

include $(CLEAR_VARS)

LOCAL_MODULE:= libavdevice_static

LOCAL_SRC_FILES:= ./build/lib/libavdevice.a

LOCAL_EXPORT_C_INCLUDES := $(LOCAL_PATH)

include $(PREBUILT_STATIC_LIBRARY)

#static version of libavfilter

include $(CLEAR_VARS)

LOCAL_MODULE:= libavfilter_static

LOCAL_SRC_FILES:= ./build/lib/libavfilter.a

LOCAL_EXPORT_C_INCLUDES := $(LOCAL_PATH)

include $(PREBUILT_STATIC_LIBRARY)

#static version of libswresample

include $(CLEAR_VARS)

LOCAL_MODULE:= libswresample_static

LOCAL_SRC_FILES:= ./build/lib/libswresample.a

LOCAL_EXPORT_C_INCLUDES := $(LOCAL_PATH)

include $(PREBUILT_STATIC_LIBRARY)

#static version of libpostproc

include $(CLEAR_VARS)

LOCAL_MODULE:= libpostproc_static

LOCAL_SRC_FILES:= ./build/lib/libpostproc.a

LOCAL_EXPORT_C_INCLUDES := $(LOCAL_PATH)

include $(PREBUILT_STATIC_LIBRARY)

#static version of libx264

include $(CLEAR_VARS)

LOCAL_MODULE:= libx264_static

LOCAL_SRC_FILES:= ./build/lib/libx264.a

LOCAL_CFLAGS := -march=armv7-a -mfloat-abi=softfp -mfpu=neon -O3 -ffast-math -funroll-loops

LOCAL_EXPORT_C_INCLUDES := $(LOCAL_PATH)

include $(PREBUILT_STATIC_LIBRARY)

include $(CLEAR_VARS)

LOCAL_MODULE := ffmpeg

LOCAL_C_INCLUDES := ./build/include \

LOCAL_SRC_FILES := decoder.c encoder.c

LOCAL_LDLIBS := -llog -lz

LOCAL_CFLAGS := -march=armv7-a -mfloat-abi=softfp -mfpu=neon -O3 -ffast-math -funroll-loops

LOCAL_WHOLE_STATIC_LIBRARIES := libavformat_static \

libavcodec_static \

libavutil_static \

libpostproc_static \

libswscale_static \

libswresample_static \

libx264_static \

libavfilter_static \

libavdevice_static \

include $(BUILD_SHARED_LIBRARY)

还需要一个Application.mk文件

APP_ABI := armeabi-v7a

APP_PLATFORM := android-15

# system - 使用默认最小的C++运行库,这样生成的应用体积小,内存占用小,但部分功能将无法支持

# stlport_static - 使用STLport作为静态库,这项是Android开发网极力推荐的

# stlport_shared - STLport 作为动态库,这个可能产生兼容性和部分低版本的Android固件,目前不推荐使用。

# gnustl_static - 使用 GNU libstdc++ 作为静态库

# 使用STLport作为静态库,这项是Android开发网极力推荐的

#APP_STL := stlport_static

APP_STL := gnustl_static

APP_CPPFLAGS := -frtti -std=gnu++11

APP_OPTIM := release

这样配置完成后的目录结构如下:

f2fa2243ad17

CodeBlog是我做的一个编程技术学习客户端,集成了很多技术网站上的博客,应用宝详情页

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值