diff --git a/ijkmediaplayer/jni/ijkplayer/Android.mk b/ijkmediaplayer/jni/ijkplayer/Android.mk index 13c9ba6a37f94db6ee8a15d934a247fd03757f74..204fdc8f35407c96aed4801f17e35fc81d9a0c50 100644 --- a/ijkmediaplayer/jni/ijkplayer/Android.mk +++ b/ijkmediaplayer/jni/ijkplayer/Android.mk @@ -21,7 +21,7 @@ LOCAL_PATH := $(call my-dir) include $(CLEAR_VARS) LOCAL_C_CFLAGS += -std=c99 -LOCAL_LDLIBS += -llog +LOCAL_LDLIBS += -llog -landroid LOCAL_C_INCLUDES += $(LOCAL_PATH) LOCAL_C_INCLUDES += $(MY_APP_FFMPEG_INCLUDE_PATH) diff --git a/ijkmediaplayer/jni/ijkplayer/ff_ffplay.c b/ijkmediaplayer/jni/ijkplayer/ff_ffplay.c index 1d34239f5bd8b107dada9a9b66c66eb0cd8ef43c..45eafa515efa89496db5a6211a0631a911472d4d 100644 --- a/ijkmediaplayer/jni/ijkplayer/ff_ffplay.c +++ b/ijkmediaplayer/jni/ijkplayer/ff_ffplay.c @@ -512,7 +512,7 @@ static int video_open(FFPlayer *ffp, int force_set_video_mode, VideoPicture *vp) is->height == ffp->screen->h && ffp->screen->h == h && !force_set_video_mode) return 0; - ffp->screen = SDL_SetVideoMode(w, h, 0, flags); + SDL_Vout_GetSurface(ffp->vout, &ffp->screen, w, h, 0); if (!ffp->screen) { fprintf(stderr, "SDL: could not set video mode - exiting\n"); return -1; diff --git a/ijkmediaplayer/jni/ijkplayer/ff_ffplay_def.h b/ijkmediaplayer/jni/ijkplayer/ff_ffplay_def.h index 258e5ccc64e7a00daadd83fdb4c0adaeebf36bc6..7531036d62affb6a18f1731a0044229f8aef27cd 100644 --- a/ijkmediaplayer/jni/ijkplayer/ff_ffplay_def.h +++ b/ijkmediaplayer/jni/ijkplayer/ff_ffplay_def.h @@ -381,9 +381,10 @@ typedef struct FFPlayer { int is_full_screen; #endif int64_t audio_callback_time; - SDL_Surface *screen; + SDL_VoutSurface *screen; /* extra fields */ + SDL_Vout *vout; int sar_num; int sar_den; @@ -445,10 +446,11 @@ inline static void ijkff_reset(FFPlayer *ffp) /* current context */ ffp->audio_callback_time = 0; - SDL_FreeSurface(ffp->screen); + SDL_Vout_FreeSurface(ffp->screen); ffp->screen = NULL; /* extra fields */ + ffp->vout = NULL; /* reset outside */ ffp->sar_num = 0; ffp->sar_den = 0; } diff --git a/ijkmediaplayer/jni/ijkplayer/ijkplayer.c b/ijkmediaplayer/jni/ijkplayer/ijkplayer.c index cdb119a6117b4cf71a31c96e301f921e23379339..3e6a3de5195662a19bf6dcdd83b73a56a2e6d7dc 100644 --- a/ijkmediaplayer/jni/ijkplayer/ijkplayer.c +++ b/ijkmediaplayer/jni/ijkplayer/ijkplayer.c @@ -44,16 +44,17 @@ IjkMediaPlayer *ijkmp_create() } memset(mp, 0, sizeof(IjkMediaPlayer)); - mp->ffplayer = malloc(sizeof(FFPlayer)); + mp->ffplayer = (FFPlayer*) malloc(sizeof(FFPlayer)); if (!mp) { free(mp); return NULL; } memset(mp->ffplayer, 0, sizeof(FFPlayer)); - FFPlayer *ffp = (FFPlayer *)&mp->ffplayer; + FFPlayer *ffp = &mp->ffplayer; ijkff_reset(ffp); + ijkmp_inc_ref(mp); return mp; } @@ -161,3 +162,13 @@ void ijkmp_reset(IjkMediaPlayer *mp) { // FIXME: implement } + +void ijkmp_set_vout(IjkMediaPlayer *mp, SDL_Vout *vout) +{ + mp->ffplayer->vout = vout; +} + +SDL_Vout *ijkmp_get_vout(IjkMediaPlayer *mp) +{ + return mp->ffplayer->vout; +} diff --git a/ijkmediaplayer/jni/ijkplayer/ijkplayer.h b/ijkmediaplayer/jni/ijkplayer/ijkplayer.h index 7d1d3abf9e700489cf4c1001e36728b7f333c983..c91788a88961c67ec6752ec6bc807a94b119c86a 100644 --- a/ijkmediaplayer/jni/ijkplayer/ijkplayer.h +++ b/ijkmediaplayer/jni/ijkplayer/ijkplayer.h @@ -26,13 +26,15 @@ #include struct IjkMediaPlayer; +typedef struct FFPlayer FFPlayer; +typedef struct SDL_Vout SDL_Vout; typedef struct IjkMediaPlayer { volatile int ref_count; - void *ffplayer; + FFPlayer *ffplayer; } IjkMediaPlayer; -// ref_count is 0 after open +// ref_count is 1 after open IjkMediaPlayer *ijkmp_create(); void ijkmp_global_init(); @@ -61,7 +63,7 @@ int ijkmp_get_current_position(IjkMediaPlayer *mp); int ijkmp_get_duration(IjkMediaPlayer *mp); void ijkmp_reset(IjkMediaPlayer *mp); -// android api -void ijkmp_set_video_surface(IjkMediaPlayer *mp, void *surface); +void ijkmp_set_vout(IjkMediaPlayer *mp, SDL_Vout *vout); +SDL_Vout *ijkmp_get_vout(IjkMediaPlayer *mp); #endif diff --git a/ijkmediaplayer/jni/ijkplayer/ijkplayer_jni.c b/ijkmediaplayer/jni/ijkplayer/ijkplayer_jni.c index f917d68fa152333d26c8f79bb608042d53aea084..f030bc4f7e4c0a8e7bddeb61034a0547dbeb0959 100644 --- a/ijkmediaplayer/jni/ijkplayer/ijkplayer_jni.c +++ b/ijkmediaplayer/jni/ijkplayer/ijkplayer_jni.c @@ -24,6 +24,7 @@ #include #include #include +#include "ijksdl/ijksdl.h" #include "ijkutil/ijkutil.h" #include "ijkplayer.h" @@ -42,7 +43,7 @@ typedef struct player_fields_t { } player_fields_t; static player_fields_t g_clazz; -static IjkMediaPlayer *get_media_player(JNIEnv* env, jobject thiz) +static IjkMediaPlayer *jni_get_media_player(JNIEnv* env, jobject thiz) { pthread_mutex_lock(&g_clazz.mutex); @@ -55,7 +56,7 @@ static IjkMediaPlayer *get_media_player(JNIEnv* env, jobject thiz) return mp; } -static IjkMediaPlayer *set_media_player(JNIEnv* env, jobject thiz, IjkMediaPlayer *mp) +static IjkMediaPlayer *jni_set_media_player(JNIEnv* env, jobject thiz, IjkMediaPlayer *mp) { pthread_mutex_lock(&g_clazz.mutex); @@ -77,11 +78,11 @@ static IjkMediaPlayer *set_media_player(JNIEnv* env, jobject thiz, IjkMediaPlaye static void IjkMediaPlayer_setDataSourceAndHeaders( - JNIEnv *env, jobject thiz, jstring path, - jobjectArray keys, jobjectArray values) + JNIEnv *env, jobject thiz, jstring path, + jobjectArray keys, jobjectArray values) { const char *c_path = NULL; - IjkMediaPlayer *mp = get_media_player(env, thiz); + IjkMediaPlayer *mp = jni_get_media_player(env, thiz); JNI_CHECK_GOTO(path, env, "java/lang/IllegalArgumentException", "mpjni: setDataSource: null path", LABEL_RETURN); JNI_CHECK_GOTO(mp, env, "java/lang/IllegalStateException", "mpjni: setDataSource: null mp", LABEL_RETURN); @@ -99,19 +100,23 @@ IjkMediaPlayer_setDataSourceAndHeaders( static void IjkMediaPlayer_setVideoSurface(JNIEnv *env, jobject thiz, jobject jsurface) { - IjkMediaPlayer *mp = get_media_player(env, thiz); + IjkMediaPlayer *mp = jni_get_media_player(env, thiz); JNI_CHECK_GOTO(mp, env, NULL, "mpjni: setVideoSurface: null mp", LABEL_RETURN); - // FIXME: implement + SDL_Vout *vout = ijkmp_get_vout(mp); + assert(vout); + + SDL_VoutAndroid_SetAndroidSurface(vout, env, jsurface); LABEL_RETURN: ijkmp_dec_ref(&mp); + return; } static void IjkMediaPlayer_prepareAsync(JNIEnv *env, jobject thiz) { - IjkMediaPlayer *mp = get_media_player(env, thiz); + IjkMediaPlayer *mp = jni_get_media_player(env, thiz); JNI_CHECK_GOTO(mp, env, "java/lang/IllegalStateException", "mpjni: prepareAsync: null mp", LABEL_RETURN); ijkmp_prepare_async(mp); @@ -123,7 +128,7 @@ IjkMediaPlayer_prepareAsync(JNIEnv *env, jobject thiz) static void IjkMediaPlayer_start(JNIEnv *env, jobject thiz) { - IjkMediaPlayer *mp = get_media_player(env, thiz); + IjkMediaPlayer *mp = jni_get_media_player(env, thiz); JNI_CHECK_GOTO(mp, env, "java/lang/IllegalStateException", "mpjni: start: null mp", LABEL_RETURN); ijkmp_start(mp); @@ -135,7 +140,7 @@ IjkMediaPlayer_start(JNIEnv *env, jobject thiz) static void IjkMediaPlayer_stop(JNIEnv *env, jobject thiz) { - IjkMediaPlayer *mp = get_media_player(env, thiz); + IjkMediaPlayer *mp = jni_get_media_player(env, thiz); JNI_CHECK_GOTO(mp, env, "java/lang/IllegalStateException", "mpjni: stop: null mp", LABEL_RETURN); ijkmp_stop(mp); @@ -147,7 +152,7 @@ IjkMediaPlayer_stop(JNIEnv *env, jobject thiz) static void IjkMediaPlayer_pause(JNIEnv *env, jobject thiz) { - IjkMediaPlayer *mp = get_media_player(env, thiz); + IjkMediaPlayer *mp = jni_get_media_player(env, thiz); JNI_CHECK_GOTO(mp, env, "java/lang/IllegalStateException", "mpjni: pause: null mp", LABEL_RETURN); ijkmp_pause(mp); @@ -160,7 +165,7 @@ static int IjkMediaPlayer_getVideoWidth(JNIEnv *env, jobject thiz) { int retval = 0; - IjkMediaPlayer *mp = get_media_player(env, thiz); + IjkMediaPlayer *mp = jni_get_media_player(env, thiz); JNI_CHECK_GOTO(mp, env, NULL, "mpjni: getVideoWidth: null mp", LABEL_RETURN); retval = ijkmp_get_video_width(mp); @@ -174,7 +179,7 @@ static int IjkMediaPlayer_getVideoHeight(JNIEnv *env, jobject thiz) { int retval = 0; - IjkMediaPlayer *mp = get_media_player(env, thiz); + IjkMediaPlayer *mp = jni_get_media_player(env, thiz); JNI_CHECK_GOTO(mp, env, NULL, "mpjni: getVideoHeight: null mp", LABEL_RETURN); retval = ijkmp_get_video_height(mp); @@ -187,7 +192,7 @@ IjkMediaPlayer_getVideoHeight(JNIEnv *env, jobject thiz) static void IjkMediaPlayer_seekTo(JNIEnv *env, jobject thiz, int msec) { - IjkMediaPlayer *mp = get_media_player(env, thiz); + IjkMediaPlayer *mp = jni_get_media_player(env, thiz); JNI_CHECK_GOTO(mp, env, "java/lang/IllegalStateException", "mpjni: seekTo: null mp", LABEL_RETURN); ijkmp_seek_to(mp, msec); @@ -200,7 +205,7 @@ static jboolean IjkMediaPlayer_isPlaying(JNIEnv *env, jobject thiz) { jboolean retval = JNI_FALSE; - IjkMediaPlayer *mp = get_media_player(env, thiz); + IjkMediaPlayer *mp = jni_get_media_player(env, thiz); JNI_CHECK_GOTO(mp, env, NULL, "mpjni: isPlaying: null mp", LABEL_RETURN); retval = ijkmp_is_playing(mp) ? JNI_TRUE : JNI_FALSE; @@ -214,7 +219,7 @@ static int IjkMediaPlayer_getCurrentPosition(JNIEnv *env, jobject thiz) { int retval = 0; - IjkMediaPlayer *mp = get_media_player(env, thiz); + IjkMediaPlayer *mp = jni_get_media_player(env, thiz); JNI_CHECK_GOTO(mp, env, NULL, "mpjni: getCurrentPosition: null mp", LABEL_RETURN); retval = ijkmp_get_current_position(mp); @@ -228,7 +233,7 @@ static int IjkMediaPlayer_getDuration(JNIEnv *env, jobject thiz) { int retval = 0; - IjkMediaPlayer *mp = get_media_player(env, thiz); + IjkMediaPlayer *mp = jni_get_media_player(env, thiz); JNI_CHECK_GOTO(mp, env, NULL, "mpjni: getDuration: null mp", LABEL_RETURN); retval = ijkmp_get_duration(mp); @@ -241,21 +246,30 @@ IjkMediaPlayer_getDuration(JNIEnv *env, jobject thiz) static void IjkMediaPlayer_release(JNIEnv *env, jobject thiz) { - IjkMediaPlayer *mp = get_media_player(env, thiz); - JNI_CHECK_GOTO(mp, env, NULL, "mpjni: release: null mp", LABEL_RETURN); + IjkMediaPlayer *mp = jni_get_media_player(env, thiz); + if (!mp) + return; // explicit close mp ijkmp_shutdown(mp); + SDL_Vout *vout = ijkmp_get_vout(mp); + if (vout) { + ijkmp_set_vout(mp, NULL); + SDL_Vout_Free(vout); + } + LABEL_RETURN: ijkmp_dec_ref(&mp); + ijkmp_dec_ref(&mp); + jni_set_media_player(env, thiz, NULL); } static void IjkMediaPlayer_reset(JNIEnv *env, jobject thiz) { // FIXME: consider create new MediaPlayer - IjkMediaPlayer *mp = get_media_player(env, thiz); + IjkMediaPlayer *mp = jni_get_media_player(env, thiz); JNI_CHECK_GOTO(mp, env, NULL, "mpjni: reset: null mp", LABEL_RETURN); ijkmp_reset(mp); @@ -273,13 +287,34 @@ IjkMediaPlayer_native_init(JNIEnv *env) static void IjkMediaPlayer_native_setup(JNIEnv *env, jobject thiz, jobject weak_this) { -// FIXME: implement + SDL_Vout *vout = NULL; + IjkMediaPlayer *mp = ijkmp_create(); + JNI_CHECK_GOTO(mp, env, "java/lang/OutOfMemoryError", "mpjni: native_setup: ijkmp_create() failed", LABEL_RETURN); + + vout = SDL_VoutAndroid_CreateForAndroidSurface(); + JNI_CHECK_GOTO(mp, env, "java/lang/OutOfMemoryError", "mpjni: native_setup: SDL_VoutAndroid_CreateAndroidSurface() failed", LABEL_RETURN); + + ijkmp_set_vout(mp, vout); + jni_set_media_player(env, thiz, mp); + + // FIXME: implement + + mp = NULL; + vout = NULL; + + LABEL_RETURN: + if (vout) + SDL_Vout_Free(vout); + if (mp) + ijkmp_dec_ref(mp); + return; } static void IjkMediaPlayer_native_finalize(JNIEnv *env, jobject thiz) { -// FIXME: implement + // FIXME: implement + IjkMediaPlayer_release(env, thiz); } // ----------------------------------------------------------------------------