android 移植ffmpeg后so库的使用

今天折腾了一天,可算是有所收获,成功的用jni调用了libffmpeg中的一个方法-----avcodec_version(),至于avcodec_version()是干什么用的我不大清楚,应该是获取版本信息吧,没有深入的去研究ffmpeg。

这里主要是想把折腾一天所获取的经验记录下来,以免时间长全忘了,也希望能给其他人一点借鉴,不至于和我一样一点头绪都没有连猜带蒙的,本文纯属个人心得,高手可以无视....

要在android上用ffmpeg首先得奖ffmpeg工程移植到android上,这里就要用到ndk把这个开源工程编译成一个后缀为so的库,这个步骤这里就不多说了 网上的资料也挺多的,我是按照:http://www.cnblogs.com/scottwong/archive/2010/12/17/1909455.html在ubantu环境下编译的,你按照教程上一步一步来应该都没有问题,顺便给下在windows下编译ffmpeg的教程:http://abitno.me/compile-ffmpeg-android-ndk(这个要用非ie浏览器打开)。以上两篇文章给了我很大的指引,在此谢过。。。都是牛人啊~~~

编译完以后你会获得一个libffmpeg.so的文件,那么问题来了,怎么用呢。我在百度,google搜了半天也没有一个详细的教程,总是东一句西一句的,但思路是明确的,就是还得编译一个so文件,这个so里的是jni方法,可以由java层调用的,而这些jni方法里用到的函数则就是来至libffmpeg.so了。思路是有了,但是具体怎么做呢?又经过一顿摸索,n次的编译,终于编译成功了。我是拿一个标准的ndk例子来做的测试就是ndk samples文件夹里的hello-jni工程。进入该工程的jni目录,将ffmpeg的源代码拷到该目录下,做这部的原因是你要编译的so文件里需要调用ffmpeg的方法,自然要引用ffmpeg里的h文件,然后将libffmpeg.so文件拷到ndk目录下的platforms/android-5/arch-arm/usr/lib目录下(你会发现platfroms里有好几个android文件夹如 -3 -4 -5分别代表不同的版本,以防万一我每个目录都拷了,呵呵,应该是只要拷指定目录的),因为等等系统编译的时候要用。接下来就编辑android.mk和hello-jni.c文件了 代码如下

android.mk

C代码  

  1. # Copyright (C) 2009 The Android Open Source Project
  2. #
  3. # Licensed under the Apache License, Version 2.0 (the "License");
  4. # you may not use this file except in compliance with the License.
  5. # You may obtain a copy of the License at
  6. #
  7. #      http://www.apache.org/licenses/LICENSE-2.0
  8. #
  9. # Unless required by applicable law or agreed to in writing, software
  10. # distributed under the License is distributed on an "AS IS" BASIS,
  11. # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  12. # See the License for the specific language governing permissions and
  13. # limitations under the License.
  14. #
  15. LOCAL_PATH := $(call my-dir)
  16. include $(CLEAR_VARS)
  17. PATH_TO_FFMPEG_SOURCE:=$(LOCAL_PATH)/ffmpeg
  18. LOCAL_C_INCLUDES += $(PATH_TO_FFMPEG_SOURCE)
  19. LOCAL_LDLIBS := -lffmpeg
  20. LOCAL_MODULE    := hello-jni
  21. LOCAL_SRC_FILES := hello-jni.c
  22. include $(BUILD_SHARED_LIBRARY)

PATH_TO_FFMPEG_SOURCE:=$(LOCAL_PATH)/ffmpeg

这行是定义一个变量,也就是ffmpeg源码的路径

LOCAL_C_INCLUDES += $(PATH_TO_FFMPEG_SOURCE)
这行是指定源代码的路径,也就是刚才拷过去的ffmpeg源码,$(LOCAL_PATH)是根目录,如果没有加这行那么引入ffmpeg库中的h文件编译就会出错说找不到该h文件。

LOCAL_LDLIBS := -lffmpeg
这行很重要,这是表示你这个so运行的时候依赖于libffmpeg.so这个库, 再举个例子:如果你要编译的so不仅要用到libffmpeg.so这个库还要用的libopencv.so这个库的话,你这个参数就应该写成

LOCAL_LDLIBS := -lffmpeg -lopencv

其他的参数都是正常的ndk编译用的了,不明白的话google一下。

hello-jni.c

C代码  

  1. /*
  2. * Copyright (C) 2009 The Android Open Source Project
  3. *
  4. * Licensed under the Apache License, Version 2.0 (the "License");
  5. * you may not use this file except in compliance with the License.
  6. * You may obtain a copy of the License at
  7. *
  8. *      http://www.apache.org/licenses/LICENSE-2.0
  9. *
  10. * Unless required by applicable law or agreed to in writing, software
  11. * distributed under the License is distributed on an "AS IS" BASIS,
  12. * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  13. * See the License for the specific language governing permissions and
  14. * limitations under the License.
  15. *
  16. */
  17. #include <string.h>
  18. #include <stdio.h>
  19. #include <android/log.h>
  20. #include <stdlib.h>
  21. #include <jni.h>
  22. #include <ffmpeg/libavcodec/avcodec.h>
  23. /* This is a trivial JNI example where we use a native method
  24. * to return a new VM String. See the corresponding Java source
  25. * file located at:
  26. *
  27. *   apps/samples/hello-jni/project/src/com/example/HelloJni/HelloJni.java
  28. */
  29. jstring
  30. Java_com_example_hellojni_HelloJni_stringFromJNI( JNIEnv* env,
  31. jobject thiz )
  32. {
  33. char str[25];
  34. sprintf(str, "%d", avcodec_version());
  35. return (*env)->NewStringUTF(env, str);
  36. }

#include <ffmpeg/libavcodec/avcodec.h>
这行是因为下面要用到avcodec_version()这个函数。

改完这两个文件以后就可以编译了~~用ndk-build命令编译完后在工程的libs/armeabi目录底下就会有一个libhello-jni.so文件了!(两行眼泪啊~终于编译成功了)

编译完成后就可以进行测试了,记得将libffmpeg.so也拷到armeabi目录底下,并在java代码中写上

Java代码  

  1. static {
  2. System.loadLibrary("ffmpeg");
  3. System.loadLibrary("hello-jni");
  4. }

HelloJni.java

Java代码  

  1. /*
  2. * Copyright (C) 2009 The Android Open Source Project
  3. *
  4. * Licensed under the Apache License, Version 2.0 (the "License");
  5. * you may not use this file except in compliance with the License.
  6. * You may obtain a copy of the License at
  7. *
  8. *      http://www.apache.org/licenses/LICENSE-2.0
  9. *
  10. * Unless required by applicable law or agreed to in writing, software
  11. * distributed under the License is distributed on an "AS IS" BASIS,
  12. * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  13. * See the License for the specific language governing permissions and
  14. * limitations under the License.
  15. */
  16. package com.example.hellojni;
  17. import android.app.Activity;
  18. import android.widget.TextView;
  19. import android.os.Bundle;
  20. public class HelloJni extends Activity
  21. {
  22. /** Called when the activity is first created. */
  23. @Override
  24. public void onCreate(Bundle savedInstanceState)
  25. {
  26. super.onCreate(savedInstanceState);
  27. /* Create a TextView and set its content.
  28. * the text is retrieved by calling a native
  29. * function.
  30. */
  31. TextView  tv = new TextView(this);
  32. tv.setText( "1111" );
  33. //System.out.println();
  34. setContentView(tv);
  35. tv.setText(String.valueOf(stringFromJNI()));
  36. }
  37. /* A native method that is implemented by the
  38. * ‘hello-jni‘ native library, which is packaged
  39. * with this application.
  40. */
  41. public native String  stringFromJNI();
  42. /* This is another native method declaration that is *not*
  43. * implemented by ‘hello-jni‘. This is simply to show that
  44. * you can declare as many native methods in your Java code
  45. * as you want, their implementation is searched in the
  46. * currently loaded native libraries only the first time
  47. * you call them.
  48. *
  49. * Trying to call this function will result in a
  50. * java.lang.UnsatisfiedLinkError exception !
  51. */
  52. public native String  unimplementedStringFromJNI();
  53. /* this is used to load the ‘hello-jni‘ library on application
  54. * startup. The library has already been unpacked into
  55. * /data/data/com.example.HelloJni/lib/libhello-jni.so at
  56. * installation time by the package manager.
  57. */
  58. static {
  59. System.loadLibrary("ffmpeg");
  60. System.loadLibrary("hello-jni");
  61. }
  62. }

到此就完成了,将程序装到手机可看到打印出“3426306”,google搜索“ffmpeg 3426306”得知果然是ffmpeg的东西,证明成功的调用了libffmpeg.so库里的方法了。欣慰啊~~

接下来要做的就是学习ffmpeg库里的各种函数的使用方法,以实现自己想要的功能了。

今天折腾了一天,可算是有所收获,成功的用jni调用了libffmpeg中的一个方法-----avcodec_version(),至于avcodec_version()是干什么用的我不大清楚,应该是获取版本信息吧,没有深入的去研究ffmpeg。

这里主要是想把折腾一天所获取的经验记录下来,以免时间长全忘了,也希望能给其他人一点借鉴,不至于和我一样一点头绪都没有连猜带蒙的,本文纯属个人心得,高手可以无视....

要在android上用ffmpeg首先得奖ffmpeg工程移植到android上,这里就要用到ndk把这个开源工程编译成一个后缀为so的库,这个步骤这里就不多说了 网上的资料也挺多的,我是按照:http://www.cnblogs.com/scottwong/archive/2010/12/17/1909455.html在ubantu环境下编译的,你按照教程上一步一步来应该都没有问题,顺便给下在windows下编译ffmpeg的教程:http://abitno.me/compile-ffmpeg-android-ndk(这个要用非ie浏览器打开)。以上两篇文章给了我很大的指引,在此谢过。。。都是牛人啊~~~

编译完以后你会获得一个libffmpeg.so的文件,那么问题来了,怎么用呢。我在百度,google搜了半天也没有一个详细的教程,总是东一句西一句的,但思路是明确的,就是还得编译一个so文件,这个so里的是jni方法,可以由java层调用的,而这些jni方法里用到的函数则就是来至libffmpeg.so了。思路是有了,但是具体怎么做呢?又经过一顿摸索,n次的编译,终于编译成功了。我是拿一个标准的ndk例子来做的测试就是ndk samples文件夹里的hello-jni工程。进入该工程的jni目录,将ffmpeg的源代码拷到该目录下,做这部的原因是你要编译的so文件里需要调用ffmpeg的方法,自然要引用ffmpeg里的h文件,然后将libffmpeg.so文件拷到ndk目录下的platforms/android-5/arch-arm/usr/lib目录下(你会发现platfroms里有好几个android文件夹如 -3 -4 -5分别代表不同的版本,以防万一我每个目录都拷了,呵呵,应该是只要拷指定目录的),因为等等系统编译的时候要用。接下来就编辑android.mk和hello-jni.c文件了 代码如下

android.mk

C代码  

  1. # Copyright (C) 2009 The Android Open Source Project
  2. #
  3. # Licensed under the Apache License, Version 2.0 (the "License");
  4. # you may not use this file except in compliance with the License.
  5. # You may obtain a copy of the License at
  6. #
  7. #      http://www.apache.org/licenses/LICENSE-2.0
  8. #
  9. # Unless required by applicable law or agreed to in writing, software
  10. # distributed under the License is distributed on an "AS IS" BASIS,
  11. # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  12. # See the License for the specific language governing permissions and
  13. # limitations under the License.
  14. #
  15. LOCAL_PATH := $(call my-dir)
  16. include $(CLEAR_VARS)
  17. PATH_TO_FFMPEG_SOURCE:=$(LOCAL_PATH)/ffmpeg
  18. LOCAL_C_INCLUDES += $(PATH_TO_FFMPEG_SOURCE)
  19. LOCAL_LDLIBS := -lffmpeg
  20. LOCAL_MODULE    := hello-jni
  21. LOCAL_SRC_FILES := hello-jni.c
  22. include $(BUILD_SHARED_LIBRARY)

PATH_TO_FFMPEG_SOURCE:=$(LOCAL_PATH)/ffmpeg

这行是定义一个变量,也就是ffmpeg源码的路径

LOCAL_C_INCLUDES += $(PATH_TO_FFMPEG_SOURCE)
这行是指定源代码的路径,也就是刚才拷过去的ffmpeg源码,$(LOCAL_PATH)是根目录,如果没有加这行那么引入ffmpeg库中的h文件编译就会出错说找不到该h文件。

LOCAL_LDLIBS := -lffmpeg
这行很重要,这是表示你这个so运行的时候依赖于libffmpeg.so这个库, 再举个例子:如果你要编译的so不仅要用到libffmpeg.so这个库还要用的libopencv.so这个库的话,你这个参数就应该写成

LOCAL_LDLIBS := -lffmpeg -lopencv

其他的参数都是正常的ndk编译用的了,不明白的话google一下。

hello-jni.c

C代码  

  1. /*
  2. * Copyright (C) 2009 The Android Open Source Project
  3. *
  4. * Licensed under the Apache License, Version 2.0 (the "License");
  5. * you may not use this file except in compliance with the License.
  6. * You may obtain a copy of the License at
  7. *
  8. *      http://www.apache.org/licenses/LICENSE-2.0
  9. *
  10. * Unless required by applicable law or agreed to in writing, software
  11. * distributed under the License is distributed on an "AS IS" BASIS,
  12. * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  13. * See the License for the specific language governing permissions and
  14. * limitations under the License.
  15. *
  16. */
  17. #include <string.h>
  18. #include <stdio.h>
  19. #include <android/log.h>
  20. #include <stdlib.h>
  21. #include <jni.h>
  22. #include <ffmpeg/libavcodec/avcodec.h>
  23. /* This is a trivial JNI example where we use a native method
  24. * to return a new VM String. See the corresponding Java source
  25. * file located at:
  26. *
  27. *   apps/samples/hello-jni/project/src/com/example/HelloJni/HelloJni.java
  28. */
  29. jstring
  30. Java_com_example_hellojni_HelloJni_stringFromJNI( JNIEnv* env,
  31. jobject thiz )
  32. {
  33. char str[25];
  34. sprintf(str, "%d", avcodec_version());
  35. return (*env)->NewStringUTF(env, str);
  36. }

#include <ffmpeg/libavcodec/avcodec.h>
这行是因为下面要用到avcodec_version()这个函数。

改完这两个文件以后就可以编译了~~用ndk-build命令编译完后在工程的libs/armeabi目录底下就会有一个libhello-jni.so文件了!(两行眼泪啊~终于编译成功了)

编译完成后就可以进行测试了,记得将libffmpeg.so也拷到armeabi目录底下,并在java代码中写上

Java代码  

  1. static {
  2. System.loadLibrary("ffmpeg");
  3. System.loadLibrary("hello-jni");
  4. }

HelloJni.java

Java代码  

  1. /*
  2. * Copyright (C) 2009 The Android Open Source Project
  3. *
  4. * Licensed under the Apache License, Version 2.0 (the "License");
  5. * you may not use this file except in compliance with the License.
  6. * You may obtain a copy of the License at
  7. *
  8. *      http://www.apache.org/licenses/LICENSE-2.0
  9. *
  10. * Unless required by applicable law or agreed to in writing, software
  11. * distributed under the License is distributed on an "AS IS" BASIS,
  12. * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  13. * See the License for the specific language governing permissions and
  14. * limitations under the License.
  15. */
  16. package com.example.hellojni;
  17. import android.app.Activity;
  18. import android.widget.TextView;
  19. import android.os.Bundle;
  20. public class HelloJni extends Activity
  21. {
  22. /** Called when the activity is first created. */
  23. @Override
  24. public void onCreate(Bundle savedInstanceState)
  25. {
  26. super.onCreate(savedInstanceState);
  27. /* Create a TextView and set its content.
  28. * the text is retrieved by calling a native
  29. * function.
  30. */
  31. TextView  tv = new TextView(this);
  32. tv.setText( "1111" );
  33. //System.out.println();
  34. setContentView(tv);
  35. tv.setText(String.valueOf(stringFromJNI()));
  36. }
  37. /* A native method that is implemented by the
  38. * ‘hello-jni‘ native library, which is packaged
  39. * with this application.
  40. */
  41. public native String  stringFromJNI();
  42. /* This is another native method declaration that is *not*
  43. * implemented by ‘hello-jni‘. This is simply to show that
  44. * you can declare as many native methods in your Java code
  45. * as you want, their implementation is searched in the
  46. * currently loaded native libraries only the first time
  47. * you call them.
  48. *
  49. * Trying to call this function will result in a
  50. * java.lang.UnsatisfiedLinkError exception !
  51. */
  52. public native String  unimplementedStringFromJNI();
  53. /* this is used to load the ‘hello-jni‘ library on application
  54. * startup. The library has already been unpacked into
  55. * /data/data/com.example.HelloJni/lib/libhello-jni.so at
  56. * installation time by the package manager.
  57. */
  58. static {
  59. System.loadLibrary("ffmpeg");
  60. System.loadLibrary("hello-jni");
  61. }
  62. }

到此就完成了,将程序装到手机可看到打印出“3426306”,google搜索“ffmpeg 3426306”得知果然是ffmpeg的东西,证明成功的调用了libffmpeg.so库里的方法了。欣慰啊~~

接下来要做的就是学习ffmpeg库里的各种函数的使用方法,以实现自己想要的功能了。

时间: 2024-08-11 05:43:26

android 移植ffmpeg后so库的使用的相关文章

直播技术总结(二)ijkplayer的编译到Android平台并测试解码库

转载请把头部出处链接和尾部二维码一起转载,本文出自逆流的鱼yuiop:http://blog.csdn.net/hejjunlin/article/details/55670380 前言:ijkplayer,是b站工程师开源的播放器框架,基于FFmpeg及MediaCodec,内部实现软解及硬解的功能,对于没有自研底层播放器的公司,用它确实是比较合适了.关于介绍可以直接看:https://github.com/Bilibili/ijkplayer,今天主要是对ijkplayer进行编译在Andr

[原]如何在Android用FFmpeg+SDL2.0解码图像线程

关于如何在Android上用FFmpeg+SDL2.0解码显示图像参考[原]如何在Android用FFmpeg+SDL2.0解码显示图像 ,关于如何在Android使用FFmpeg+SDL2.0解码声音参考[原]如何在Android用FFmpeg+SDL2.0解码声音.但是该文章有一个问题,就是解码出来的声音有很大的噪音,基本无法听清,这是由于对于声音的处理有问题.故本文参考ffmpeg-sdl音频播放分析声音解码的处理,解码出来的声音就正常了. 博主的开发环境:Ubuntu 14.04 64位

成功在mini2440上移植ffmpeg ----fwqlzz love is for ever

在mini2440上,整个移植过程分三个步骤:(1)编译x264:(2)编译ffmpeg:(3)移植成功后,进行测试,即使用ffmpeg录像. (1)编译x264 官网上下了个最新的x264,地址http://www.videolan.org/developers/x264.html.我下载的文件是last_x264.tar.bz2. 120版本地址 http://pan.baidu.com/s/1jG81TSq 解压命令为#tar  -jxv  -f  last_x264.tar.bz2,

拇指接龙游戏从WIN32向Android移植过程问题记录(2)

本文中,在前文(1)基础上,将尽可能详细记录拇指接龙游戏从WIN32向Android移植过程后期--UI运行级调试出现的问题及可能的解决办法. 问题1 正未运行,问题就来了.忽然发现,工程左上角挂着一个大大的感叹号!请看截图: 打开工程属性对话框,观察到如下现象: 我把鼠标停留在右边的横线处,后面出现一个关键单词missing.也就是说,我们的游戏工程依赖的cocos2d-x库包jar文件丢失了!? 再打开另一处观察,发现如下: 其实,有一个重要细节在上一篇中我没有交待.此前,我使用中家的版本在

Ogre 1.9 Android移植

Ogre 1.9 Android移植 分类: 图形渲染2013-02-04 16:47 3860人阅读 评论(14) 收藏 举报 Android Ogre C++linuxLinuxLINUX 上一篇博客,将1.8.1这个版本移植到了Android平台,无奈着不是官方版本,不太完美.这次尝试为Android平台构建1.9版本(注意这是个不稳定版本,1.9官方没有正式Release). 依赖库官方已经移植好了,直接下载下来就可以了. 地址 http://sourceforge.net/projec

cocos2d-x 从win32到android移植的全套解决方案

引言:我们使用cocos2d-x引擎制作了一款飞行射击游戏,其中创新性地融入了手势识别功能.但是我们在移植过程中遇到了很多的问题,同时也发现网上的资料少而不全.所以在项目行将结束的时候,我们特地写了这篇文章来完整记录我们整个移植的过程,纪念我们项目的成功完成,更以此来表达对帮助过我们的人的感谢.移植过程中我们在网上得到了很多帮助,更要感谢黄杨学长在最后时刻帮助我们突破难关! 0.开发平台 系统:win8 profession 64bit IDE:vs2012 rtm, eclipse cocos

【转载】cocos2dx 中 Android NDK 加载动态库的问题

原文地址:http://blog.csdn.net/sozell/article/details/10551309 cocos2dx 中 Android NDK 加载动态库的问题 闲聊 最近在接入各个平台的SDK,遇到了不少问题,也从中了解了不少知识,之前一直觉得没啥好写的,毕竟做了4个月的游戏开发,也没有碰上什么真正的大问题,cocos2dx的引擎包得也很好,能让人把大部分时间都关注在游戏逻辑.效果的处理上,当然,之前的libevent还是小坑一下,但是和后来遇到的相比,也算不上什么了. 我最

Android Studio中导入第三方库

之前开发Android都是使用的eclipse,最近由于和外国朋友Timothy一起开发一款应用,他是从WP平台刚切换使用Android的,使用的开发环境时Android Studio,为了便于项目的交流,我便尝试着去使用Android Studio.刚开始用遇到一个问题:如何在Android Studio中导入第三方库? 首先本人使用的Studio版本为0.5.8,尝试解决方法如下,分两种: 1.导入jar包 直接复制你的jar包(如actiobarsherlock.jar)至工程的libs目

移植ffmpeg到VC环境心得

所有想学习ffmpeg的网友有福了,大名鼎鼎的ffmpeg,移植到Windows的VC6版本全部开源,编译环境为VC6+SP5+VCPP5.别忘记了顶贴哦. 移植ffmpeg到windows,主要的修改是ffmpeg中VC6不支持C99语法,简单移植步骤如下: 1:首先装好Linux.VMware和SDL,配置好smb,在Linux下编译通过,验证能正确的Run. 2:把Linux下相应目录的所有文件通过smb拖到Windows,以后的修改移植都在Windows下进行. 3:对照所有同名的.c文