之前写了FFmpeg的编译过程,那么编译之后,就是用来实际的开发了,开发之前,首先要把FFmpeg的lib和include集成到我们的项目。这一篇主要介绍如何集成到Android项目。
1、新建Android工程
这个就不用说了吧......
2、创建JNI Folder
不知道怎么创建的我的另外一篇文章Android JNI之HelloWorld ,这里我们修改一下路径:
我这里的路径为:app/jnicode/jni
3、在jincode下新建一个prebuilt文件夹,把编译出来的文件拷贝进来:
屏幕快照 2016-09-14 16.14.28.png如上图所示,我这里说明一下:
- prebuilt :存放FFmpeg的头文件。
- jni:存放的是自己的C/C++代码
- arm32:32位处理器的libs
- arm64 : 64位处理器的libs
- autobuild.sh : 自动编译的脚本
- autojavah.sh : 自动把Java文件转换为头文件的脚本
4、编写自己的mk文件:
我们这里以32位架构处理器来说明,大家都知道,要使用mk文件编译一个文件,需要放置在jni文件夹下(不知道这样表述是否正确,目前接触到的都是这样的),所以在arm32下新建一个jni目录,还是上个图吧,比照着图片来说,更详细一些。
屏幕快照 2016-09-14 16.48.47.pngps:不知道为什么截的图越小,图片就被放的很大,反倒是截的图片大了显示的很小,好郁闷。。。。。。
- libs :放置ffmpeg的so文件
- Android.mk
- Application.mk
与jni平级的两个目录是编译的时候自动生成的。还有两个mk文件,就不用我解释了吧。
这里主要看一下Android.mk文件里面的内容
LOCAL_PATH:= $(call my-dir) #指定当前目录
PRE_BUILD_PATH:= $(LOCAL_PATH)/../../prebuilt #指定FFmpeg的头文件目录
MY_SRC_PATH:=$(LOCAL_PATH)/../../jni #指定自己的C代码路径
#************************libavcodec********************************/
include $(CLEAR_VARS)
LOCAL_MODULE:= libavcodec
LOCAL_SRC_FILES:= libs/libavcodec-57.so
LOCAL_EXPORT_C_INCLUDES := $(PRE_BUILD_PATH)/libffmpeg/libavcodec
include $(PREBUILT_SHARED_LIBRARY)
#************************libavformat********************************/
include $(CLEAR_VARS)
LOCAL_MODULE:= libavformat
LOCAL_SRC_FILES:= libs/libavformat-57.so
LOCAL_EXPORT_C_INCLUDES := $(PRE_BUILD_PATH)/libffmpeg/libavformat
include $(PREBUILT_SHARED_LIBRARY)
#************************libswscale********************************/
include $(CLEAR_VARS)
LOCAL_MODULE:= libswscale
LOCAL_SRC_FILES:= libs/libswscale-4.so
LOCAL_EXPORT_C_INCLUDES := $(PRE_BUILD_PATH)/libffmpeg/libswscale
include $(PREBUILT_SHARED_LIBRARY)
#************************libavutil********************************/
include $(CLEAR_VARS)
LOCAL_MODULE:= libavutil
LOCAL_SRC_FILES:= libs/libavutil-55.so
LOCAL_EXPORT_C_INCLUDES := $(PRE_BUILD_PATH)/libffmpeg/libavutil
include $(PREBUILT_SHARED_LIBRARY)
#************************libavfilter********************************/
include $(CLEAR_VARS)
LOCAL_MODULE:= libavfilter
LOCAL_SRC_FILES:= libs/libavfilter-6.so
LOCAL_EXPORT_C_INCLUDES := $(PRE_BUILD_PATH)/libffmpeg/libavfilter
include $(PREBUILT_SHARED_LIBRARY)
#************************libavfilter********************************/
include $(CLEAR_VARS)
LOCAL_MODULE:= libpostproc
LOCAL_SRC_FILES:= libs/libpostproc-54.so
LOCAL_EXPORT_C_INCLUDES := $(PRE_BUILD_PATH)/libffmpeg/libpostproc
include $(PREBUILT_SHARED_LIBRARY)
#************************libswresample********************************/
include $(CLEAR_VARS)
LOCAL_MODULE:= libswresample
LOCAL_SRC_FILES:= libs/libswresample-2.so
LOCAL_EXPORT_C_INCLUDES := $(PRE_BUILD_PATH)/libffmpeg/libswresample
include $(PREBUILT_SHARED_LIBRARY)
#************************libx264********************************/
include $(CLEAR_VARS)
LOCAL_MODULE:= libx264
LOCAL_SRC_FILES:= libs/libx264.a
LOCAL_EXPORT_C_INCLUDES := $(PRE_BUILD_PATH)/libffmpeg/libx264
include $(PREBUILT_STATIC_LIBRARY)
include $(CLEAR_VARS)
LOCAL_MODULE := playerCore #指定自己的so文件名称
#需要编译的自己的C文件
LOCAL_SRC_FILES:= $(MY_SRC_PATH)/org_eson_ffmpeg_libs_PlayerCore.cpp \
LOCAL_LDLIBS += -llog -ljnigraphics -lz -landroid -lOpenSLES -g
#引入FFmpeg,这个如果不添加,编译时会报错
LOCAL_SHARED_LIBRARIES := libavcodec libavformat libswscale libavutil libavfilter libswresample
include $(BUILD_SHARED_LIBRARY)
其实,这里的libx264是可以不用要的,我这里也添加上了。可以自行忽略。至于Application.mk 的内容,这里就贴出来了。
5、修改FFmpeg的头文件
这里先说一下为什么要修改
1、作为一个Java程序员,习惯用代码的自动提示,如果不修改,在写的时候,不能自动提示,感觉好郁闷,也可以说是自己的技术还很渣,严重依赖代码的提示。(毕竟自动提示写代码很快,但还是需要改改,这里记一下以后再写代码的时候能不用就不用,对自己提高有帮助)
2、编译64位时会报错
解决方法:
1、修改头文件的引用路径(以libavcodec/avcodec.h为例):
将
#include "libavutil/samplefmt.h"
#include "libavutil/attributes.h"
#include "libavutil/avutil.h"
#include "libavutil/buffer.h"
#include "libavutil/cpu.h"
#include "libavutil/channel_layout.h"
#include "libavutil/dict.h"
#include "libavutil/frame.h"
#include "libavutil/log.h"
#include "libavutil/pixfmt.h"
#include "libavutil/rational.h"
改为:
#include "../libavutil/samplefmt.h"
#include "../libavutil/attributes.h"
#include "../libavutil/avutil.h"
#include "../libavutil/buffer.h"
#include "../libavutil/cpu.h"
#include "../libavutil/channel_layout.h"
#include "../libavutil/dict.h"
#include "../libavutil/frame.h"
#include "../libavutil/log.h"
#include "../libavutil/pixfmt.h"
#include "../libavutil/rational.h"
以自己的路径为准,我这里只是参考。
2、在编译64位时libutils/common.h会报错,如果 common.h 报错
在最上面添加以下代码
#ifndef UINT64_C
#define UINT64_C(value)__CONCAT(value,ULL)
#endif
总结
FFmpeg的编译和集成到这里就结束了,后续有可能更新具体的实现某些功能,有时间在更新吧。
疑问
关于同时编译出64位和32位架构的so库时,感觉现在模式比较麻烦,不知道还能不能优化,希望有大神看到指点一下。感谢!
网友评论