Mac环境下Android Studio移植FFmpeg

准备:

1. Android Studio
2. FFmpeg-2.8.4  
3. android-ndk-r10e

一、ndk编译ffmpeg

1.下载ffmpeg和ndk

ffmpeg下载地址:http://ffmpeg.org/download.html  我下载的是2.8.4版本
ndk 官网下载,这个我就不说了,自备梯子翻越长城。。我下载的是 android-ndk-r10e 

2.解压ffmpeg和ndk

将解压的ffmpeg文件夹复制到 android-ndk-r10e ->sources 目录中
修改文件夹ffmpeg-2.8.4中configure脚本,由于编译出来的动态库文件名的版本号在.so之后(例如“libavcodec.so.5.100.1”),而android平台不能识别这样文件名,所以需要修改这种文件名。在configure文件中找到下面几行代码:
SLIBNAME_WITH_MAJOR='$(SLIBNAME).$(LIBMAJOR)'
LIB_INSTALL_EXTRA_CMD='$$(RANLIB)"$(LIBDIR)/$(LIBNAME)"'
SLIB_INSTALL_NAME='$(SLIBNAME_WITH_VERSION)'
SLIB_INSTALL_LINKS='$(SLIBNAME_WITH_MAJOR)$(SLIBNAME)'

修改为:
SLIBNAME_WITH_MAJOR='$(SLIBPREF)$(FULLNAME)-$(LIBMAJOR)$(SLIBSUF)'
LIB_INSTALL_EXTRA_CMD='$$(RANLIB)"$(LIBDIR)/$(LIBNAME)"'
SLIB_INSTALL_NAME='$(SLIBNAME_WITH_MAJOR)'
SLIB_INSTALL_LINKS='$(SLIBNAME)'

3.配置编译脚本

在文件夹ffmpeg-2.8.4中新建脚本 build_android.sh 
#!/bin/bash
export NDK=/Users/huxing/Downloads/android-ndk-r10e
export PREBUILT=$NDK/toolchains/arm-linux-androideabi-4.8/prebuilt
export PLATFORM=$NDK/platforms/android-21/arch-arm
export PREFIX=../simplefflib
build_one(){
  ./configure --target-os=linux --prefix=$PREFIX \
--enable-cross-compile \
--enable-runtime-cpudetect \
--disable-asm \
--arch=arm \
--cc=$PREBUILT/darwin-x86_64/bin/arm-linux-androideabi-gcc \
--cross-prefix=$PREBUILT/darwin-x86_64/bin/arm-linux-androideabi- \
--disable-stripping \
--nm=$PREBUILT/darwin-x86_64/bin/arm-linux-androideabi-nm \
--sysroot=$PLATFORM \
--enable-gpl --enable-shared --disable-static --enable-small \
--disable-ffprobe --disable-ffplay --disable-ffmpeg --disable-ffserver --disable-debug \
--extra-cflags="-fPIC -DANDROID -D__thumb__ -mthumb -Wfatal-errors -Wno-deprecated -mfloat-abi=softfp -marm -march=armv7-a" 
}

build_one

make
make install
注意的是前面三个路径替换成自己的路径,还有一些不同版本ndk路径的取名不同比如darwin-x86_64有的是linux-x86_64,自己注意一下路径名称

4.编译ffmpeg

使用命令cd到脚本目录下,首先 chmod a+x build_android.sh 授权,然后 ./build_android.sh 运行脚本。
编译需要花一些时间,编译完成之后就会在android-ndk-r10e -> source 目录下多出一个 simplefflib 目录
(还有8个.so文件被我删除了)

二、Android Studio 部分

1.新建 Android Studio工程

新建AS工程,在main目录下新建一个jni目录,在gradle.properties配置中添加 android.useDeprecatedNdk = true,在Project Structure中配置ndk location,指向你下载ndk的路径
再将编译的FFmpeg文件复制到jni目录中。

2.配置build.gradle

取消自动编译,添加 :
 sourceSets.main.jni.srcDirs = []
添加ndk配置:
ndk {
            moduleName "helloffmpeg"
            abiFilter "armeabi"
            ldLibs "log", "z", "m", "jnigraphics", "android"
        }
全部配置为如下:
apply plugin: 'com.android.application'

android {
    compileSdkVersion 23
    buildToolsVersion "23.0.0"

    sourceSets.main.jni.srcDirs = []
    defaultConfig {
        applicationId "hxing.com.myffmpeg"
        minSdkVersion 19
        targetSdkVersion 23
        versionCode 1
        versionName "1.0"

        ndk {
            moduleName "helloffmpeg"
            abiFilter "armeabi"
            ldLibs "log", "z", "m", "jnigraphics", "android"
        }
    }
    buildTypes {
        release {
            minifyEnabled false
            proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
        }
    }
}

3.生成头文件

在MainActivity.class中添加Native方法和调用库文件,如下:
public class MainActivity extends AppCompatActivity {

    static {
        System.loadLibrary("helloffmpeg");
        System.loadLibrary("avutil-54");
        System.loadLibrary("avcodec-56");
        System.loadLibrary("avformat-56");
        System.loadLibrary("avdevice-56");
        System.loadLibrary("swresample-1");
        System.loadLibrary("swscale-3");
        System.loadLibrary("postproc-53");
        System.loadLibrary("avfilter-5");
    }

    public native String getffmpegFromJNI();

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        TextView textView = (TextView) findViewById(R.id.text);
        textView.setText(getffmpegFromJNI());

    }
}


打开as的Terminal窗口,默认路径是当前项目根路径,输入以下命令:
cd app/src/main/java
javah -d ../jni hxing.com.myffmpeg.MainActivity

进入java目录下 使用javah命令在jni目录下生成头文件,然后再在jni目录下建立对应的c文件,c文件代码如下:
//
// Created by 胡醒 on 15/12/31.
//
#include <jni.h>
#include "libavcodec/avcodec.h"

JNIEXPORT jstring JNICALL Java_hxing_com_myffmpeg_MainActivity_getffmpegFromJNI
        (JNIEnv * env, jobject thiz){
    char info[10000] = { 0 };
    sprintf(info, "%s\n", avcodec_configuration());
    return (*env)->NewStringUTF(env, info);
}



4.在jni目录下建立Android.mk文件

LOCAL_PATH := $(call my-dir)

# FFmpeg library
include $(CLEAR_VARS)
LOCAL_MODULE := avcodec
LOCAL_SRC_FILES := lib/libavcodec-56.so
include $(PREBUILT_SHARED_LIBRARY)

include $(CLEAR_VARS)
LOCAL_MODULE := avdevice
LOCAL_SRC_FILES := lib/libavdevice-56.so
include $(PREBUILT_SHARED_LIBRARY)

include $(CLEAR_VARS)
LOCAL_MODULE := avfilter
LOCAL_SRC_FILES := lib/libavfilter-5.so
include $(PREBUILT_SHARED_LIBRARY)

include $(CLEAR_VARS)
LOCAL_MODULE := avformat
LOCAL_SRC_FILES := lib/libavformat-56.so
include $(PREBUILT_SHARED_LIBRARY)

include $(CLEAR_VARS)
LOCAL_MODULE := avutil
LOCAL_SRC_FILES := lib/libavutil-54.so
include $(PREBUILT_SHARED_LIBRARY)

include $(CLEAR_VARS)
LOCAL_MODULE := postproc
LOCAL_SRC_FILES := lib/libpostproc-53.so
include $(PREBUILT_SHARED_LIBRARY)

include $(CLEAR_VARS)
LOCAL_MODULE := swresample
LOCAL_SRC_FILES := lib/libswresample-1.so
include $(PREBUILT_SHARED_LIBRARY)

include $(CLEAR_VARS)
LOCAL_MODULE := swscale
LOCAL_SRC_FILES := lib/libswscale-3.so
include $(PREBUILT_SHARED_LIBRARY)

# Program
include $(CLEAR_VARS)
LOCAL_MODULE := helloffmpeg
LOCAL_SRC_FILES := hxing_com_myffmpeg_MainActivity.c
LOCAL_C_INCLUDES += $(LOCAL_PATH)/include
LOCAL_LDLIBS := -llog -lz
LOCAL_SHARED_LIBRARIES := avcodec avdevice avfilter avformat avutil postproc swresample swscale
include $(BUILD_SHARED_LIBRARY)

还可以在当前目录下建立Application.mk,这个文件用来指定编译的平台,我这里只指定armeabi
APP_ABI := armeabi


5.编译ffmpeg.so文件

进入Terminal窗口,输入命令 “ cd ../jni” 返回到jni目录中,在输入命令:
/Users/huxing/Downloads/android-ndk-r10e/ndk-build NDK_PROJECT_PATH=null APP_BUILD_SCRIPT=/Users/huxing/Documents/myFFmpeg2/app/src/main/jni/Android.mk APP_PLATFORM=android-21 NDK_OUT=/Users/huxing/Documents/myFFmpeg2/app/build/intermediates/ndk/debug/obj NDK_LIBS_OUT=/Users/huxing/Documents/myFFmpeg2/app/build/intermediates/ndk/debug/lib APP_ABI=armeabi

/Users/huxing/Downloads/android-ndk-r10e/ndk-build :你安装的ndk目录中的ndk-build命令
APP_BUILD_SCRIPT :工程中jni目录下的android.mk的路径
NDK_OUT : 输出路径
NDK_LIBS_OUT :库文件输出路径
APP_ABI : 输出平台
改成自己工程对应的目录

6.运行工程

成功调用ffmpeg方法输出信息


猜你喜欢

转载自blog.csdn.net/huxing0215/article/details/50442356