Android studio3.1.3 FFmpeg編譯和使用命令給視頻添加水印

本人第一次寫(xiě)文章试躏,因?yàn)閷?duì)于一個(gè)剛接觸ffmpeg的人來(lái)說(shuō)編譯SO和在Android studio上編譯中遇到了很多坑,所以身心體會(huì)了里面的很多坑设褐,所以寫(xiě)這篇文章颠蕴,希望對(duì)大家有用

本文中又多個(gè)庫(kù)和單個(gè)庫(kù)的編譯,大家可以自由選擇

首先編譯FFmpeg推薦裝個(gè)虛擬機(jī)然后用Ubuntu來(lái)編譯

首先去FFmpeg官網(wǎng)去下載Download FFmpeg 4.0版的助析,然后在Android官網(wǎng)下載NDK建議使用r14版本犀被,高的版本會(huì)出現(xiàn)問(wèn)題NDK r14版本下載地方

在很多文章中需要修改ffmpeg里面configure文件,但也可以不用修改外冀,在創(chuàng)建編譯腳本得時(shí)候加上--target-os=android \寡键,就可以編譯需要得編譯庫(kù)

下面是創(chuàng)建build_android.sh腳本


#!/bin/sh

export NDK_HOME=/home/guoliang/Downloads/android-ndk-r14b

export NDK_HOST_PLATFORM=linux-x86_64

PREFIX=android-build

COMMON_OPTIONS="\

    --prefix=android/ \

    --target-os=android \

    --disable-static \

    --enable-shared \

    --enable-small \

    --disable-programs \

    --disable-ffmpeg \

    --disable-ffplay \

    --disable-ffprobe \

    --disable-doc \

    --disable-symver \

    --disable-asm \

    "

function build_android {

    ./configure \

    --libdir=${PREFIX}/libs/armeabi-v7a \

    --incdir=${PREFIX}/includes/armeabi-v7a \

    --pkgconfigdir=${PREFIX}/pkgconfig/armeabi-v7a \

    --arch=arm \

    --cpu=armv7-a \

    --cross-prefix="${NDK_HOME}/toolchains/arm-linux-androideabi-4.9/prebuilt/${NDK_HOST_PLATFORM}/bin/arm-linux-androideabi-" \

    --sysroot="${NDK_HOME}/platforms/android-19/arch-arm/" \

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

    --extra-ldexeflags=-pie \

    ${COMMON_OPTIONS}

    make clean

    make -j8 && make install

    ./configure \

    --libdir=${PREFIX}/libs/arm64-v8a \

    --incdir=${PREFIX}/includes/arm64-v8a \

    --pkgconfigdir=${PREFIX}/pkgconfig/arm64-v8a \

    --arch=aarch64 \

    --cpu=armv8-a \

    --cross-prefix="${NDK_HOME}/toolchains/aarch64-linux-android-4.9/prebuilt/${NDK_HOST_PLATFORM}/bin/aarch64-linux-android-" \

    --sysroot="${NDK_HOME}/platforms/android-21/arch-arm64/" \

    --extra-ldexeflags=-pie \

    ${COMMON_OPTIONS}

    make clean

    make -j8 && make install

    ./configure \

    --libdir=${PREFIX}/libs/x86 \

    --incdir=${PREFIX}/includes/x86 \

    --pkgconfigdir=${PREFIX}/pkgconfig/x86 \

    --arch=x86 \

    --cpu=i686 \

    --cross-prefix="${NDK_HOME}/toolchains/x86-4.9/prebuilt/${NDK_HOST_PLATFORM}/bin/i686-linux-android-" \

    --sysroot="${NDK_HOME}/platforms/android-19/arch-x86/" \

    --extra-ldexeflags=-pie \

    ${COMMON_OPTIONS}

    make clean

    make -j8 && make install

    ./configure \

    --libdir=${PREFIX}/libs/x86_64 \

    --incdir=${PREFIX}/includes/x86_64 \

    --pkgconfigdir=${PREFIX}/pkgconfig/x86_64 \

    --arch=x86_64 \

    --cpu=x86_64 \

    --cross-prefix="${NDK_HOME}/toolchains/x86_64-4.9/prebuilt/${NDK_HOST_PLATFORM}/bin/x86_64-linux-android-" \

    --sysroot="${NDK_HOME}/platforms/android-21/arch-x86_64/" \

    --extra-ldexeflags=-pie \

    ${COMMON_OPTIONS}

    make clean

    make -j8 && make install

};

build_android

NDK_HOME配置你的文件目錄

NDK_HOST_PLATFORM配置64位

在ffmpeg文件目錄下打開(kāi)終端運(yùn)行,下面兩條命令
chmod +x build_android.sh
./build_android.sh

下面是得到得文件

image

下來(lái)把includes和libs拷貝出來(lái)(記得要壓縮雪隧,虛擬機(jī)拷貝需要是壓縮文件才行)

創(chuàng)建一個(gè)支持C++的項(xiàng)目把編譯出來(lái)的文件放入項(xiàng)目中

image

下面這個(gè)是獲取8個(gè)庫(kù)的包和一個(gè)so庫(kù)(FFmpeg3.3.7版本)


make clean

export NDK=/home/guoliang/Downloads/android-ndk-r14b

export PREBUILT=$NDK/toolchains/arm-linux-androideabi-4.9/prebuilt

export PLATFORM=$NDK/platforms/android-14/arch-arm

export PREFIX=./android/$CPU-vfp

build_one(){

  ./configure --target-os=linux --prefix=$PREFIX \

--enable-cross-compile \

--enable-runtime-cpudetect \

--disable-asm \

--arch=arm \

--cc=$PREBUILT/linux-x86_64/bin/arm-linux-androideabi-gcc \

--cross-prefix=$PREBUILT/linux-x86_64/bin/arm-linux-androideabi- \

--disable-stripping \

--nm=$PREBUILT/linux-x86_64/bin/arm-linux-androideabi-nm \

--sysroot=$PLATFORM \

--enable-gpl --enable-static --disable-shared --enable-nonfree --enable-version3 --enable-small \

--enable-zlib --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

$PREBUILT/linux-x86_64/bin/arm-linux-androideabi-ld -rpath-link=$PLATFORM/usr/lib -L$PLATFORM/usr/lib -L$PREFIX/lib -soname libffmpeg.so -shared -nostdlib -Bsymbolic --whole-archive --no-undefined -o $PREFIX/libffmpeg.so libavcodec/libavcodec.a libavfilter/libavfilter.a libswresample/libswresample.a libavformat/libavformat.a libavutil/libavutil.a libswscale/libswscale.a libpostproc/libpostproc.a libavdevice/libavdevice.a -lc -lm -lz -ldl -llog --dynamic-linker=/system/bin/linker $PREBUILT/linux-x86_64/lib/gcc/arm-linux-androideabi/4.9.x/libgcc.a

cd ..

image

export PREFIX=./android/$CPU-vfp

這個(gè)字段后面是生成文件的所在地

上面獲取8個(gè)包和單個(gè)SO庫(kù)西轩,效果是一樣的员舵,但對(duì)于后面的步驟來(lái)說(shuō)更為方便(都是針對(duì)于arm,如需其他可以替換上面的字段)

切記把整個(gè)ffmpeg文件壓縮藕畔,不是單獨(dú)壓縮編譯好的文件马僻,因?yàn)楹竺娌襟E需要ffmpeg源碼里面的文件

下面是配置Android studio如何加載編譯好的文件

第一步創(chuàng)建新的項(xiàng)目

image

勾選位包涵c++項(xiàng)目,省去很多步驟

image

這一步看各自的需求來(lái)勾選注服,本人是這樣勾選的

第二步copy文件

image

畫(huà)紅線的是接下來(lái)會(huì)修改的文件韭邓,下面就是把咱們編譯好的文件copy進(jìn)入

image

畫(huà)圈的地方就是需要咱們編譯好的文件copy進(jìn)去,是不是感覺(jué)很簡(jiǎn)單祠汇,其實(shí)這才是剛剛開(kāi)始仍秤,大家會(huì)注意到我有兩個(gè)地方劃了紅線,這兩個(gè)文件需要大家自己建立可很,(這個(gè)時(shí)候就是需要咱們壓縮好的ffmpeg源碼的壓縮文件了)然后從咱們ffmpeg里面獲取這幾個(gè)文件然后copy進(jìn)入就可以了(因?yàn)楹笃诰幾g會(huì)遇到一些文件诗力,提前放進(jìn)去)

第三部 修改文件

修改app下build.gradle文件

image

紅框的地方是需要添加的

abiFilters 后面配置需要用armeabi-v7a ,因?yàn)锳ndroid studio3.1.3已經(jīng)不讓用 armeabi

下來(lái)需要修改CMakeLists.txt文件


cmake_minimum_required(VERSION 3.4.1)

add_library( # Sets the name of the library.

native-lib

# Sets the library as a shared library.

SHARED

# Provides a relative path to your source file(s).

src/main/cpp/native-lib.cpp )

add_library( ffmpeg #切記不要用libffmpeg

SHARED

IMPORTED )

set_target_properties( ffmpeg

PROPERTIES IMPORTED_LOCATION

../../../../libs/${ANDROID_ABI}/libffmpeg.so)

find_library( # Sets the name of the path variable.

log-lib

# Specifies the name of the NDK library that

# you want CMake to locate.

log )

set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -std=gnu++11")

include_directories(src/main/cpp)

include_directories(src/main/cpp/include)

target_link_libraries( # Specifies the target library.

native-lib

ffmpeg

# Links the target library to the log library

# included in the NDK.

${log-lib} )

切記不要用libffmpeg起別名我抠,因?yàn)橛盟脑挄?huì)編譯的時(shí)候會(huì)報(bào)錯(cuò)苇本,本人就是被坑了

下面點(diǎn)擊一下

image

然后運(yùn)行一下項(xiàng)目看有沒(méi)有錯(cuò)誤,如果按上面的步驟走的

image

當(dāng)出現(xiàn)這個(gè)頁(yè)面那說(shuō)明上面的步驟都已經(jīng)沒(méi)有問(wèn)題了菜拓,如果出現(xiàn)錯(cuò)誤請(qǐng)檢查代碼和步驟

下面需要從ffmepg文件里面copy這幾個(gè)文件瓣窄,cmdutils.c、cmdutils.h纳鼎、cmdutils_common_opts.h俺夕、config.h、ffmpeg.c贱鄙、ffmpeg.h劝贸、ffmpeg_filter.c、ffmpeg_opt.c

image

然后修改CMakeLists.txt文件


cmake_minimum_required(VERSION 3.4.1)

add_library( # Sets the name of the library.

native-lib

# Sets the library as a shared library.

SHARED

# Provides a relative path to your source file(s).

src/main/cpp/ffmpeg/cmdutils.c

src/main/cpp/ffmpeg/ffmpeg.c

src/main/cpp/ffmpeg/ffmpeg_filter.c

src/main/cpp/ffmpeg/ffmpeg_opt.c

src/main/cpp/native-lib.cpp )

add_library( ffmpeg #切記不要用libffmpeg

SHARED

IMPORTED )

set_target_properties( ffmpeg

PROPERTIES IMPORTED_LOCATION

../../../../libs/${ANDROID_ABI}/libffmpeg.so)

find_library( # Sets the name of the path variable.

log-lib

# Specifies the name of the NDK library that

# you want CMake to locate.

log )

set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -std=gnu++11")

include_directories(src/main/cpp)

include_directories(src/main/cpp/include)

target_link_libraries( # Specifies the target library.

native-lib

ffmpeg

# Links the target library to the log library

# included in the NDK.

${log-lib} )

然后點(diǎn)擊Refresh Linked C++ Projects 選項(xiàng)逗宁,然后點(diǎn)擊Rebuild Project選項(xiàng)映九,接下在會(huì)報(bào)一些錯(cuò)誤

image

然后從ffmpeg文件中copy這些沒(méi)有的文件到項(xiàng)目中,等沒(méi)有引入包錯(cuò)誤的時(shí)候瞎颗,有的時(shí)候還會(huì)報(bào)錯(cuò)件甥,比如

image

這個(gè)時(shí)候不要點(diǎn)藍(lán)色的區(qū)域這樣?xùn)|西是永遠(yuǎn)改不完的,這是時(shí)候你需要看紅線上面的錯(cuò)誤哼拔,它的錯(cuò)誤的意思是包的路徑?jīng)]有給正確

image

把上面的修改一下再點(diǎn)擊Rebuild Project選項(xiàng)編譯就好了引有,這個(gè)時(shí)候咱們已經(jīng)離成功不遠(yuǎn)了

第三步使用命令編輯視頻

下面我們?cè)谶@里寫(xiě)入一個(gè)方法

image

然后ALT+Enter就生成文件了,下面我們要修文件

image

把native-lib.cpp修改為native-lib.c,切記也要修改CmakeList.text里面的代碼倦逐,要不然會(huì)出問(wèn)題

image
image

下面添加代碼如下

image

#include

#include

JNIEXPORT jint JNICALL

Java_com_example_myapplication_MainActivity_ffmpegRun(JNIEnv *env, jobject instance,

                                                      jobjectArray cmd) {

int argc = (*env)->GetArrayLength(env, cmd);

    char *argv[argc];

    int i;

    for (i =0; i < argc; i++) {

jstring js = (jstring) (*env)->GetObjectArrayElement(env, cmd, i);

        argv[i] = (char*) (*env)->GetStringUTFChars(env, js, 0);

    }

return run(argc, argv);

}

編譯一下報(bào)紅線的會(huì)消失譬正,下面我們就可以添加水印了,準(zhǔn)備一個(gè)視頻和圖片在根目錄下,下來(lái)修改MainActivity文件


package com.example.myapplication;

import android.os.Environment;

import android.support.v7.app.AppCompatActivity;

import android.os.Bundle;

import android.util.Log;

import android.view.View;

import android.widget.TextView;

import android.widget.Toast;

public class MainActivityextends AppCompatActivity {

// Used to load the 'native-lib' library on application startup.

    static {

System.loadLibrary("native-lib");

        System.loadLibrary("ffmpeg");

    }

@Override

    protected void onCreate(Bundle savedInstanceState) {

super.onCreate(savedInstanceState);

        setContentView(R.layout.activity_main);

        // Example of a call to a native method

        TextView tv = (TextView) findViewById(R.id.sample_text);

        tv.setOnClickListener(new View.OnClickListener() {

@Override

            public void onClick(View view) {

String base = Environment.getExternalStorageDirectory().getPath();

                Log.e("PATH", base);

                String[] commands =new String[9];

                commands[0] ="ffmpeg";

                //輸入

                commands[1] ="-i";

                commands[2] = base +"/input.mp4";

                //水印

                commands[3] ="-i";

                commands[4] = base +"/ic_launcher.png";//此處的圖片地址換成帶透明通道的視頻就可以合成動(dòng)態(tài)視頻遮罩导帝。

                commands[5] ="-filter_complex";

                commands[6] ="[1:v]scale=300:300[s];[0:v][s]overlay=50:10";

                //覆蓋輸出

                commands[7] ="-y";//直接覆蓋輸出文件

//輸出文件

                commands[8] = base +"/merge.mp4";

                int result = ffmpegRun(commands);

                if (result==0){

Toast.makeText(MainActivity.this, "命令執(zhí)行完成", Toast.LENGTH_SHORT).show();

                }

}

});

    }

public native int ffmpegRun(String[] cmd);

}

運(yùn)行的時(shí)候會(huì)卡主守谓,過(guò)一會(huì)就好了,因?yàn)樵谥骶€程操作的您单,這個(gè)可以由大家自由修改

image.png
image.png

切記要加這兩個(gè)權(quán)限斋荞,6.0以上把動(dòng)態(tài)權(quán)限給上
然后就成功添加水印

這個(gè)是項(xiàng)目地址大家可以作為參考
git :https://github.com/GuoLiangGod/MyFFmpeg

第一次寫(xiě)文章因?yàn)檫@個(gè)地方小坑有的多,所以才寫(xiě)這篇文件虐秦,希望對(duì)大家又幫助平酿,如果遇到問(wèn)題可以留言

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個(gè)濱河市悦陋,隨后出現(xiàn)的幾起案子蜈彼,更是在濱河造成了極大的恐慌,老刑警劉巖俺驶,帶你破解...
    沈念sama閱讀 222,104評(píng)論 6 515
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件幸逆,死亡現(xiàn)場(chǎng)離奇詭異,居然都是意外死亡暮现,警方通過(guò)查閱死者的電腦和手機(jī)还绘,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 94,816評(píng)論 3 399
  • 文/潘曉璐 我一進(jìn)店門(mén),熙熙樓的掌柜王于貴愁眉苦臉地迎上來(lái)栖袋,“玉大人拍顷,你說(shuō)我怎么就攤上這事√练” “怎么了昔案?”我有些...
    開(kāi)封第一講書(shū)人閱讀 168,697評(píng)論 0 360
  • 文/不壞的土叔 我叫張陵,是天一觀的道長(zhǎng)电媳。 經(jīng)常有香客問(wèn)我踏揣,道長(zhǎng),這世上最難降的妖魔是什么匆背? 我笑而不...
    開(kāi)封第一講書(shū)人閱讀 59,836評(píng)論 1 298
  • 正文 為了忘掉前任呼伸,我火速辦了婚禮身冀,結(jié)果婚禮上钝尸,老公的妹妹穿的比我還像新娘。我一直安慰自己搂根,他們只是感情好珍促,可當(dāng)我...
    茶點(diǎn)故事閱讀 68,851評(píng)論 6 397
  • 文/花漫 我一把揭開(kāi)白布。 她就那樣靜靜地躺著剩愧,像睡著了一般猪叙。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上,一...
    開(kāi)封第一講書(shū)人閱讀 52,441評(píng)論 1 310
  • 那天穴翩,我揣著相機(jī)與錄音犬第,去河邊找鬼。 笑死芒帕,一個(gè)胖子當(dāng)著我的面吹牛歉嗓,可吹牛的內(nèi)容都是我干的。 我是一名探鬼主播背蟆,決...
    沈念sama閱讀 40,992評(píng)論 3 421
  • 文/蒼蘭香墨 我猛地睜開(kāi)眼鉴分,長(zhǎng)吁一口氣:“原來(lái)是場(chǎng)噩夢(mèng)啊……” “哼!你這毒婦竟也來(lái)了带膀?” 一聲冷哼從身側(cè)響起志珍,我...
    開(kāi)封第一講書(shū)人閱讀 39,899評(píng)論 0 276
  • 序言:老撾萬(wàn)榮一對(duì)情侶失蹤,失蹤者是張志新(化名)和其女友劉穎垛叨,沒(méi)想到半個(gè)月后伦糯,有當(dāng)?shù)厝嗽跇?shù)林里發(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 46,457評(píng)論 1 318
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡嗽元,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 38,529評(píng)論 3 341
  • 正文 我和宋清朗相戀三年舔株,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片还棱。...
    茶點(diǎn)故事閱讀 40,664評(píng)論 1 352
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡载慈,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出珍手,到底是詐尸還是另有隱情办铡,我是刑警寧澤,帶...
    沈念sama閱讀 36,346評(píng)論 5 350
  • 正文 年R本政府宣布琳要,位于F島的核電站寡具,受9級(jí)特大地震影響,放射性物質(zhì)發(fā)生泄漏稚补。R本人自食惡果不足惜童叠,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 42,025評(píng)論 3 334
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望课幕。 院中可真熱鬧厦坛,春花似錦、人聲如沸乍惊。這莊子的主人今日做“春日...
    開(kāi)封第一講書(shū)人閱讀 32,511評(píng)論 0 24
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽(yáng)润绎。三九已至撬碟,卻和暖如春诞挨,著一層夾襖步出監(jiān)牢的瞬間,已是汗流浹背呢蛤。 一陣腳步聲響...
    開(kāi)封第一講書(shū)人閱讀 33,611評(píng)論 1 272
  • 我被黑心中介騙來(lái)泰國(guó)打工惶傻, 沒(méi)想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留,地道東北人其障。 一個(gè)月前我還...
    沈念sama閱讀 49,081評(píng)論 3 377
  • 正文 我出身青樓达罗,卻偏偏與公主長(zhǎng)得像,于是被迫代替她去往敵國(guó)和親静秆。 傳聞我的和親對(duì)象是個(gè)殘疾皇子粮揉,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 45,675評(píng)論 2 359

推薦閱讀更多精彩內(nèi)容