android调用jni使用ffmeg把h264转yuv数据
2016-11-06 13:06
447 查看
jni代码部分:
java调用函数.
#include <stdio.h> #include <time.h> #include "libavcodec/avcodec.h" #include "libavformat/avformat.h" #include "libswscale/swscale.h" #include "libavutil/log.h" #include "libavutil/frame.h" #ifdef ANDROID #include <jni.h> #include <android/log.h> #define LOGE(format, ...) __android_log_print(ANDROID_LOG_ERROR, "(>_<)", format, ##__VA_ARGS__) #define LOGI(format, ...) __android_log_print(ANDROID_LOG_INFO, "(^_^)", format, ##__VA_ARGS__) #else #define LOGE(format, ...) printf("(>_<) " format "\n", ##__VA_ARGS__) #define LOGI(format, ...) printf("(^_^) " format "\n", ##__VA_ARGS__) #endif AVFormatContext *pFormatCtx; int i, videoindex; AVCodecContext *pCodecCtx; AVCodec *pCodec; AVFrame *pFrame; uint8_t *out_buffer; AVPacket packet; int y_size; int ret, got_picture; struct SwsContext *img_convert_ctx; int frame_cnt; clock_t time_start, time_finish; double time_duration = 0.0; char input_str[500]={0}; char info[1000]={0}; //Output FFmpeg's av_log() void custom_log(void *ptr, int level, const char* fmt, va_list vl){ FILE *fp=fopen("/storage/emulated/0/av_log.txt","a+"); if(fp){ vfprintf(fp,fmt,vl); fflush(fp); fclose(fp); } } JNIEXPORT jint JNICALL Java_com_aac_utils_DecodeYUV_init (JNIEnv *env, jobject obj) { av_log_set_callback(custom_log); av_register_all(); pCodec = avcodec_find_decoder(AV_CODEC_ID_H264); pCodecCtx = avcodec_alloc_context3(pCodec); if(pCodec==NULL){ LOGE("Couldn't find Codec.\n"); return -1; } if(avcodec_open2(pCodecCtx, pCodec,NULL)<0){ LOGE("Couldn't open codec.\n"); return -1; } pFrame= avcodec_alloc_frame(); pCodecCtx->flags |= CODEC_FLAG_LOW_DELAY; pCodecCtx->debug |= FF_DEBUG_MMCO; pCodecCtx->pix_fmt = PIX_FMT_YUV420P; } JNIEXPORT jint JNICALL Java_com_aac_utils_DecodeYUV_decode (JNIEnv *env, jobject obj, jbyteArray jin_packet,jbyteArray jout_packet,jint jwidth,jint jheight) { av_init_packet(&packet); unsigned char *in_array =(*env)->GetByteArrayElements(env,jin_packet, 0); jbyte *out_array =(*env)->GetByteArrayElements(env,jout_packet, 0); jsize *length = (*env)->GetArrayLength(env,jin_packet); packet.size = length; packet.data = in_array; int width =jwidth; int height = jheight; ret = avcodec_decode_video2(pCodecCtx, pFrame, &got_picture, &packet); av_free_packet(&packet); if(ret < 0){ LOGE("Decode Error.\n"); return -1; } if(got_picture){ y_size=width*height; unsigned char *buf = (unsigned char *)malloc(y_size*3/2); memset(buf, 0, y_size*3/2); memcpy(buf,pFrame->data[0], y_size); memcpy(buf+y_size,pFrame->data[1], y_size / 4); memcpy(buf+y_size*5/4,pFrame->data[2], y_size / 4); jbyte *buff; buff = (jbyte*)buf; (*env)->ReleaseByteArrayElements(env,jout_packet, out_array, 0); (*env)->SetByteArrayRegion(env,jout_packet, 0, y_size*3/2, buff); free(buf); } //flush decoder //FIX: Flush Frames remained in Codec return 0; } JNIEXPORT jint JNICALL Java_com_aac_utils_DecodeYUV_close (JNIEnv *env, jobject obj) { av_frame_free(&pFrame); avcodec_close(pCodecCtx); av_free(pCodecCtx); }
java调用函数.
public class DecodeYUV { //JNI public static native int close(); public static native int init(); public static native int decode(byte[] inarray,byte[] outarray,int width,int height); }
相关文章推荐
- Android JNI入门第五篇——基本数据类型使用
- Android使用JNI实现Java与C之间传递数据
- Android驱动使用JNI调用
- android开发(26) 和其他应用交换数据方式一,使用intent指定自定义action调用其他程序里的activity,并获得其返回的结果
- 使用jni调用ffmpeg.so中的H264解码函数播放文件
- Android JNI入门第五篇——基本数据类型使用
- Android使用JNI实现Java与C之间传递数据 .
- Android(安卓)开发通过NDK调用JNI,使用opencv做本地c++代码开发配置方法 边缘检测 范例代码
- Android使用百度地图SDK调用百度地图时,发生错误 com.baidu.platform.comjni.map.basemap.JNIBaseMap.Create
- Android使用JNI实现Java与C之间传递数据
- Android使用JNI实现Java与C之间传递数据
- Android中简单的JNI使用,C++调用JAVA
- Android使用JNI实现Java与C之间传递数据
- 编译代码在Android中使用JNI调用Opencv本地代码 配置方式 边缘检测 范例代码
- Android使用JNI实现Java与C之间传递数据
- Android使用JNI实现Java与C之间传递数据
- Android之使用JNI调用NDK
- Android JNI 使用的数据结构JNINativeMethod详解 ||建立Android SDK下的JNI、JAVA应用完整步骤---Android JAVA调用C++代码
- Android使用JNI实现Java与C之间传递数据
- Android使用JNI实现Java与C之间传递数据