Hello,

(Apparently the Libav-user Archives<http://ffmpeg.org/pipermail/libav-user/> 
are empty, sorry if this had been discussed before, ok if you just give me a 
pointer.)

I'm trying to display a jpeg image sent from Java in Windows through a socket 
to a Java server in Fedora which connects directly to libav through JNI. But 
I'm having problems with libav usage, not much info so need the steps and 
functions to use as well as parameters.

Currently I:

- init the codec using av_register_all, create an AVCodec object from 
av_codec_find_decoder_by_name, a context from avcodec_alloc_context, 
avcodec_open, avcodec_alloc_frame, get pointer to AVPacket and av_malloc its 
data.

- get the raw frame buffer using env's NewDirectByteBuffer with the 
av_malloc'ed mem and size

- put a byte array from the socket into the raw frame buffer

- decode using avcodec_decode_video2

- get a decoded NewDirectByteBuffer with the av_malloc'ed data array's 
height-element and linesize plane times height.


I got this all from an internet widget, so not sure how it works or what 
parameters to pass along, or how to interpret the data before or after the 
decode. Any help greatly appreciated. Bellow the widget found from the net:


#include <jni.h>
#include "JNI_VideoCodec.h"
extern "C" {
   #include "libavcodec/avcodec.h"
   #include "libavformat/avformat.h"
}
#include <map>
#include <iostream>


using namespace std;




/*typedef*/ struct AVParams {
   AVCodec *avCodec;
   AVCodecContext *codecCtx;
   AVFrame *avFrame;
   AVPacket *avPacket;
   int rawSize;
   int height;
};




map <jint, AVParams *> objectMap;


// Created by the author, means that he is actually knowledgeable of JNIEnv
// and is making direct use of it!! (Though apparently just to keep track of 
each instance that calls the codec?)
jint get_av_uid(JNIEnv * env, jobject obj) {
   jclass cls = env->GetObjectClass(obj);
   jfieldID fid = env->GetFieldID(cls, "uid", "I");
   return env->GetIntField(obj, fid);
}


JNIEXPORT void JNICALL Java_JNI_1VideoCodec_freeResources (JNIEnv * env, 
jobject obj) {
   AVParams *avParams = objectMap[get_av_uid(env, obj)];
   av_free(avParams->avCodec);
   av_free(avParams->codecCtx);
   av_free(avParams->avFrame);
   av_free(avParams->avPacket);
}


JNIEXPORT jboolean JNICALL Java_JNI_1VideoCodec_init (JNIEnv * env, jobject 
obj, jstring codecName, jint width, jint height, jint bufferSize) {
   av_register_all();

   const char *c_string = env->GetStringUTFChars(codecName, 0);


   cout << c_string << "\n";

   AVCodec *avCodec = avcodec_find_decoder_by_name(c_string);
   if (avCodec == 0) {
      return JNI_FALSE;
   }

   AVCodecContext *codecCtx = avcodec_alloc_context();
   if (codecCtx == 0) {
      return JNI_FALSE;
   }


   if (avcodec_open(codecCtx, avCodec) != 0) {
      av_free(avCodec);
      av_free(codecCtx);
      return JNI_FALSE;
   }


   AVFrame *avFrame = avcodec_alloc_frame();
   if (avFrame == 0) {
      return JNI_FALSE;
   }


   AVPacket *avPacket = new AVPacket();
   avPacket->data = (uint8_t*) av_malloc(bufferSize);

   AVParams *avParams = new AVParams();
   avParams->avCodec = avCodec;
   avParams->codecCtx = codecCtx;
   avParams->avFrame = avFrame;
   avParams->avPacket = avPacket;
   avParams->rawSize = bufferSize;
   avParams->height = height;


   objectMap[get_av_uid(env, obj)] = avParams;


  return JNI_TRUE;
}


JNIEXPORT jobject JNICALL Java_JNI_1VideoCodec_getDecodedFrameBuffer(JNIEnv 
*env, jobject obj, jint plane) {
   AVParams *avParams = objectMap[get_av_uid(env, obj)];
   int height = plane == 0 ? avParams->height : avParams->height / 2;
   return env->NewDirectByteBuffer(avParams->avFrame->data[plane], (jlong) 
(avParams->avFrame->linesize[plane] * height));
}


JNIEXPORT jobject JNICALL Java_JNI_1VideoCodec_getRawFrameBuffer(JNIEnv *env, 
jobject obj) {
   AVParams *avParams = objectMap[get_av_uid(env, obj)];
   return env->NewDirectByteBuffer(avParams->avPacket->data, (jlong) 
(avParams->rawSize));
}


JNIEXPORT jint JNICALL Java_JNI_1VideoCodec_decodeFrame(JNIEnv *env, jobject 
obj, jint size) {
   AVParams *avParams = objectMap[get_av_uid(env, obj)];
   avParams->avPacket->size = size;
   int got_picture;
   avcodec_decode_video2(avParams->codecCtx, avParams->avFrame, &got_picture, 
avParams->avPacket);
    return got_picture;
}

_______________________________________________
Libav-user mailing list
[email protected]
http://ffmpeg.org/mailman/listinfo/libav-user

Reply via email to