From 229b30ed8bcc943ea94fee59fa5617012efeb079 Mon Sep 17 00:00:00 2001 From: Dhilan007 Date: Thu, 17 Jul 2014 21:10:26 +0800 Subject: [PATCH] Fixed VideoPlayer can't quitting the full screen mode by press the back key. --- .../cocos2dx/lib/Cocos2dxGLSurfaceView.java | 1 + .../org/cocos2dx/lib/Cocos2dxVideoHelper.java | 51 +++++++++- .../org/cocos2dx/lib/Cocos2dxVideoView.java | 92 ++++++++++--------- cocos/ui/UIVideoPlayer.h | 2 +- cocos/ui/UIVideoPlayerAndroid.cpp | 83 +++++++++-------- cocos/ui/UIVideoPlayerIOS.mm | 4 +- 6 files changed, 147 insertions(+), 86 deletions(-) diff --git a/cocos/platform/android/java/src/org/cocos2dx/lib/Cocos2dxGLSurfaceView.java b/cocos/platform/android/java/src/org/cocos2dx/lib/Cocos2dxGLSurfaceView.java index a710f8a711..58ecf41465 100644 --- a/cocos/platform/android/java/src/org/cocos2dx/lib/Cocos2dxGLSurfaceView.java +++ b/cocos/platform/android/java/src/org/cocos2dx/lib/Cocos2dxGLSurfaceView.java @@ -292,6 +292,7 @@ public class Cocos2dxGLSurfaceView extends GLSurfaceView { public boolean onKeyDown(final int pKeyCode, final KeyEvent pKeyEvent) { switch (pKeyCode) { case KeyEvent.KEYCODE_BACK: + Cocos2dxVideoHelper.mVideoHandler.sendEmptyMessage(Cocos2dxVideoHelper.KeyEventBack); case KeyEvent.KEYCODE_MENU: case KeyEvent.KEYCODE_DPAD_LEFT: case KeyEvent.KEYCODE_DPAD_RIGHT: diff --git a/cocos/platform/android/java/src/org/cocos2dx/lib/Cocos2dxVideoHelper.java b/cocos/platform/android/java/src/org/cocos2dx/lib/Cocos2dxVideoHelper.java index 64d1cc0adf..8d13e01f72 100644 --- a/cocos/platform/android/java/src/org/cocos2dx/lib/Cocos2dxVideoHelper.java +++ b/cocos/platform/android/java/src/org/cocos2dx/lib/Cocos2dxVideoHelper.java @@ -40,7 +40,7 @@ public class Cocos2dxVideoHelper { private FrameLayout mLayout = null; private Cocos2dxActivity mActivity = null; private SparseArray sVideoViews = null; - private static VideoHandler mVideoHandler = null; + static VideoHandler mVideoHandler = null; Cocos2dxVideoHelper(Cocos2dxActivity activity,FrameLayout layout) { @@ -64,6 +64,8 @@ public class Cocos2dxVideoHelper { private final static int VideoTaskSetVisible = 9; private final static int VideoTaskRestart = 10; private final static int VideoTaskKeepRatio = 11; + private final static int VideoTaskFullScreen = 12; + final static int KeyEventBack = 13; static class VideoHandler extends Handler{ WeakReference mReference; @@ -101,6 +103,16 @@ public class Cocos2dxVideoHelper { helper._setVideoRect(msg.arg1, rect.left, rect.top, rect.right, rect.bottom); break; } + case VideoTaskFullScreen:{ + Cocos2dxVideoHelper helper = mReference.get(); + Rect rect = (Rect)msg.obj; + if (msg.arg2 == 1) { + helper._setFullScreenEnabled(msg.arg1, true, rect.right, rect.bottom); + } else { + helper._setFullScreenEnabled(msg.arg1, false, rect.right, rect.bottom); + } + break; + } case VideoTaskPause: { Cocos2dxVideoHelper helper = mReference.get(); helper._pauseVideo(msg.arg1); @@ -144,6 +156,11 @@ public class Cocos2dxVideoHelper { } break; } + case KeyEventBack: { + Cocos2dxVideoHelper helper = mReference.get(); + helper.onBackKeyEvent(); + break; + } default: break; } @@ -255,6 +272,38 @@ public class Cocos2dxVideoHelper { } } + public static void setFullScreenEnabled(int index,boolean enabled, int width,int height) { + Message msg = new Message(); + msg.what = VideoTaskFullScreen; + msg.arg1 = index; + if (enabled) { + msg.arg2 = 1; + } else { + msg.arg2 = 0; + } + msg.obj = new Rect(0, 0, width, height); + mVideoHandler.sendMessage(msg); + } + + private void _setFullScreenEnabled(int index, boolean enabled, int width,int height) { + Cocos2dxVideoView videoView = sVideoViews.get(index); + if (videoView != null) { + videoView.setFullScreenEnabled(enabled, width, height); + } + } + + private void onBackKeyEvent() { + int viewCount = sVideoViews.size(); + for (int i = 0; i < viewCount; i++) { + int key = sVideoViews.keyAt(i); + Cocos2dxVideoView videoView = sVideoViews.get(key); + if (videoView != null) { + videoView.setFullScreenEnabled(false, 0, 0); + mActivity.runOnGLThread(new VideoEventRunnable(key, 1024)); + } + } + } + public static void startVideo(int index) { Message msg = new Message(); msg.what = VideoTaskStart; diff --git a/cocos/platform/android/java/src/org/cocos2dx/lib/Cocos2dxVideoView.java b/cocos/platform/android/java/src/org/cocos2dx/lib/Cocos2dxVideoView.java index f701f7b375..11ca29a137 100644 --- a/cocos/platform/android/java/src/org/cocos2dx/lib/Cocos2dxVideoView.java +++ b/cocos/platform/android/java/src/org/cocos2dx/lib/Cocos2dxVideoView.java @@ -18,7 +18,6 @@ package org.cocos2dx.lib; import android.app.AlertDialog; -import android.content.Context; import android.content.DialogInterface; import android.content.Intent; import android.content.res.AssetFileDescriptor; @@ -27,7 +26,6 @@ import android.media.AudioManager; import android.media.MediaPlayer; import android.media.MediaPlayer.OnErrorListener; import android.net.Uri; -import android.util.AttributeSet; import android.util.Log; import android.view.MotionEvent; import android.view.SurfaceHolder; @@ -75,7 +73,7 @@ public class Cocos2dxVideoView extends SurfaceView implements MediaPlayerControl // recording the seek position while preparing private int mSeekWhenPrepared; - protected Context mContext = null; + protected Cocos2dxActivity mCocos2dxActivity = null; protected int mViewLeft = 0; protected int mViewTop = 0; @@ -87,27 +85,17 @@ public class Cocos2dxVideoView extends SurfaceView implements MediaPlayerControl protected int mVisibleWidth = 0; protected int mVisibleHeight = 0; + protected boolean mFullScreenEnabled = false; + protected int mFullScreenWidth = 0; + protected int mFullScreenHeight = 0; + private int mViewTag = 0; - public Cocos2dxVideoView(Context context,int tag) { - super(context); + public Cocos2dxVideoView(Cocos2dxActivity activity,int tag) { + super(activity); mViewTag = tag; - mContext = context; - initVideoView(); - } - - public Cocos2dxVideoView(Context context, AttributeSet attrs) { - this(context, attrs, 0); - - mContext = context; - initVideoView(); - } - - public Cocos2dxVideoView(Context context, AttributeSet attrs, int defStyle) { - super(context, attrs, defStyle); - - mContext = context; + mCocos2dxActivity = activity; initVideoView(); } @@ -115,11 +103,11 @@ public class Cocos2dxVideoView extends SurfaceView implements MediaPlayerControl protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { if (mVideoWidth == 0 || mVideoHeight == 0) { setMeasuredDimension(mViewWidth, mViewHeight); - Log.e(TAG, ""+mViewWidth+ ":" +mViewHeight); + Log.i(TAG, ""+mViewWidth+ ":" +mViewHeight); } else { setMeasuredDimension(mVisibleWidth, mVisibleHeight); - Log.e(TAG, ""+mVisibleWidth+ ":" +mVisibleHeight); + Log.i(TAG, ""+mVisibleWidth+ ":" +mVisibleHeight); } } @@ -131,6 +119,18 @@ public class Cocos2dxVideoView extends SurfaceView implements MediaPlayerControl mViewHeight = maxHeight; if (mVideoWidth != 0 && mVideoHeight != 0) { + fixSize(mViewLeft, mViewTop, mViewWidth, mVideoHeight); + } + } + + public void setFullScreenEnabled(boolean enabled, int width, int height) { + if (mFullScreenEnabled != enabled) { + mFullScreenEnabled = enabled; + if (width != 0 && height != 0) { + mFullScreenWidth = width; + mFullScreenHeight = height; + } + fixSize(); } } @@ -265,7 +265,7 @@ public class Cocos2dxVideoView extends SurfaceView implements MediaPlayerControl // TODO: these constants need to be published somewhere in the framework. Intent i = new Intent("com.android.music.musicservicecommand"); i.putExtra("command", "pause"); - mContext.sendBroadcast(i); + mCocos2dxActivity.sendBroadcast(i); // we shouldn't clear the target state, because somebody might have // called start() previously @@ -288,10 +288,10 @@ public class Cocos2dxVideoView extends SurfaceView implements MediaPlayerControl mDuration = -1; mCurrentBufferPercentage = 0; if (isAssetRouse) { - AssetFileDescriptor afd = mContext.getAssets().openFd(fileName); + AssetFileDescriptor afd = mCocos2dxActivity.getAssets().openFd(fileName); mMediaPlayer.setDataSource(afd.getFileDescriptor(),afd.getStartOffset(),afd.getLength()); } else { - mMediaPlayer.setDataSource(mContext, mUri); + mMediaPlayer.setDataSource(mCocos2dxActivity, mUri); } mMediaPlayer.prepareAsync(); @@ -321,27 +321,35 @@ public class Cocos2dxVideoView extends SurfaceView implements MediaPlayerControl } public void fixSize() { - if (mViewWidth != 0 && mViewHeight != 0) { + if (mFullScreenEnabled) { + fixSize(0, 0, mFullScreenWidth, mFullScreenHeight); + } else { + fixSize(mViewLeft, mViewTop, mViewWidth, mVideoHeight); + } + } + + public void fixSize(int left,int top,int width,int height) { + if (width != 0 && height != 0) { if (mKeepRatio) { - if ( mVideoWidth * mViewHeight > mViewWidth * mVideoHeight ) { - mVisibleWidth = mViewWidth; - mVisibleHeight = mViewWidth * mVideoHeight / mVideoWidth; - } else if ( mVideoWidth * mViewHeight < mViewWidth * mVideoHeight ) { - mVisibleWidth = mViewHeight * mVideoWidth / mVideoHeight; - mVisibleHeight = mViewHeight; + if ( mVideoWidth * height > width * mVideoHeight ) { + mVisibleWidth = width; + mVisibleHeight = width * mVideoHeight / mVideoWidth; + } else if ( mVideoWidth * height < width * mVideoHeight ) { + mVisibleWidth = height * mVideoWidth / mVideoHeight; + mVisibleHeight = height; } - mVisibleLeft = mViewLeft + (mViewWidth - mVisibleWidth) / 2; - mVisibleTop = mViewTop + (mViewHeight - mVisibleHeight) / 2; + mVisibleLeft = left + (width - mVisibleWidth) / 2; + mVisibleTop = top + (height - mVisibleHeight) / 2; } else { - mVisibleLeft = mViewLeft; - mVisibleTop = mViewTop; - mVisibleWidth = mViewWidth; - mVisibleHeight = mViewHeight; + mVisibleLeft = left; + mVisibleTop = top; + mVisibleWidth = width; + mVisibleHeight = height; } } else { - mVisibleLeft = mViewLeft; - mVisibleTop = mViewTop; + mVisibleLeft = left; + mVisibleTop = top; mVisibleWidth = mVideoWidth; mVisibleHeight = mVideoHeight; } @@ -437,7 +445,7 @@ public class Cocos2dxVideoView extends SurfaceView implements MediaPlayerControl * longer have a window, don't bother showing the user an error. */ if (getWindowToken() != null) { - Resources r = mContext.getResources(); + Resources r = mCocos2dxActivity.getResources(); int messageId; if (framework_err == MediaPlayer.MEDIA_ERROR_NOT_VALID_FOR_PROGRESSIVE_PLAYBACK) { @@ -451,7 +459,7 @@ public class Cocos2dxVideoView extends SurfaceView implements MediaPlayerControl int titleId = r.getIdentifier("VideoView_error_title", "string", "android"); int buttonStringId = r.getIdentifier("VideoView_error_button", "string", "android"); - new AlertDialog.Builder(mContext) + new AlertDialog.Builder(mCocos2dxActivity) .setTitle(r.getString(titleId)) .setMessage(messageId) .setPositiveButton(r.getString(buttonStringId), diff --git a/cocos/ui/UIVideoPlayer.h b/cocos/ui/UIVideoPlayer.h index 81d0787236..deb029aaee 100644 --- a/cocos/ui/UIVideoPlayer.h +++ b/cocos/ui/UIVideoPlayer.h @@ -73,7 +73,7 @@ namespace experimental{ virtual void addEventListener(const VideoPlayer::ccVideoPlayerCallback& callback); - virtual void onPlayEvent(VideoPlayer::EventType event); + virtual void onPlayEvent(int event); virtual void draw(Renderer *renderer, const Mat4& transform, uint32_t flags) override; protected: diff --git a/cocos/ui/UIVideoPlayerAndroid.cpp b/cocos/ui/UIVideoPlayerAndroid.cpp index a9deb991f3..588107c3b9 100644 --- a/cocos/ui/UIVideoPlayerAndroid.cpp +++ b/cocos/ui/UIVideoPlayerAndroid.cpp @@ -37,10 +37,10 @@ //----------------------------------------------------------------------------------------------------------- #define CLASS_NAME "org/cocos2dx/lib/Cocos2dxVideoHelper" -void executeVideoCallback(int index,int event); - USING_NS_CC; +static void executeVideoCallback(int index,int event); + extern "C" { void Java_org_cocos2dx_lib_Cocos2dxVideoHelper_nativeExecuteVideoCallback(JNIEnv * env, jobject obj, jint index,jint event) { executeVideoCallback(index,event); @@ -87,6 +87,17 @@ void setVideoRectJNI(int index,int left,int top,int width,int height) } } +void setFullScreenEnabledJni(int index,bool enabled, int width, int height) +{ + JniMethodInfo t; + + if (JniHelper::getStaticMethodInfo(t, CLASS_NAME, "setFullScreenEnabled", "(IZII)V")) { + t.env->CallStaticVoidMethod(t.classID, t.methodID, index, enabled, width, height); + + t.env->DeleteLocalRef(t.classID); + } +} + void setVideoURLJNI(int index,int videoSource,const std::string& videoUrl) { JniMethodInfo t; @@ -166,16 +177,6 @@ VideoPlayer::VideoPlayer() { _videoPlayerIndex = createVideoWidgetJNI(); s_allVideoPlayers[_videoPlayerIndex] = this; - - auto listener = EventListenerKeyboard::create(); - listener->onKeyReleased = [&](EventKeyboard::KeyCode keycode, cocos2d::Event* event){ - if (keycode == EventKeyboard::KeyCode::KEY_BACKSPACE && _fullScreenEnabled) - { - this->setFullScreenEnabled(false); - } - }; - - _eventDispatcher->addEventListenerWithSceneGraphPriority(listener, this); } VideoPlayer::~VideoPlayer() @@ -202,31 +203,23 @@ void VideoPlayer::draw(Renderer* renderer, const Mat4 &transform, uint32_t flags { cocos2d::ui::Widget::draw(renderer,transform,flags); - if ((flags&FLAGS_TRANSFORM_DIRTY) || _fullScreenDirty) + if (flags & FLAGS_TRANSFORM_DIRTY) { - _fullScreenDirty = false; auto directorInstance = Director::getInstance(); auto glView = directorInstance->getOpenGLView(); auto frameSize = glView->getFrameSize(); - if (_fullScreenEnabled) - { - setVideoRectJNI(_videoPlayerIndex,0,0,frameSize.width,frameSize.height); - } - else - { - auto winSize = directorInstance->getWinSize(); + auto winSize = directorInstance->getWinSize(); - auto leftBottom = convertToWorldSpace(Point::ZERO); - auto rightTop = convertToWorldSpace(Point(_contentSize.width,_contentSize.height)); + auto leftBottom = convertToWorldSpace(Point::ZERO); + auto rightTop = convertToWorldSpace(Point(_contentSize.width,_contentSize.height)); - auto uiLeft = frameSize.width / 2 + (leftBottom.x - winSize.width / 2 ) * glView->getScaleX(); - auto uiTop = frameSize.height /2 - (rightTop.y - winSize.height / 2) * glView->getScaleY(); + auto uiLeft = frameSize.width / 2 + (leftBottom.x - winSize.width / 2 ) * glView->getScaleX(); + auto uiTop = frameSize.height /2 - (rightTop.y - winSize.height / 2) * glView->getScaleY(); - setVideoRectJNI(_videoPlayerIndex,uiLeft,uiTop, - (rightTop.x - leftBottom.x) * glView->getScaleX(), - (rightTop.y - leftBottom.y) * glView->getScaleY()); - } + setVideoRectJNI(_videoPlayerIndex,uiLeft,uiTop, + (rightTop.x - leftBottom.x) * glView->getScaleX(), + (rightTop.y - leftBottom.y) * glView->getScaleY()); } #if CC_VIDEOPLAYER_DEBUG_DRAW @@ -241,7 +234,9 @@ void VideoPlayer::setFullScreenEnabled(bool enabled) if (_fullScreenEnabled != enabled) { _fullScreenEnabled = enabled; - _fullScreenDirty = true; + + auto frameSize = Director::getInstance()->getOpenGLView()->getFrameSize(); + setFullScreenEnabledJni(_videoPlayerIndex, enabled, frameSize.width, frameSize.height); } } @@ -344,17 +339,25 @@ void VideoPlayer::addEventListener(const VideoPlayer::ccVideoPlayerCallback& cal _eventCallback = callback; } -void VideoPlayer::onPlayEvent(VideoPlayer::EventType event) +void VideoPlayer::onPlayEvent(int event) { - if (event == VideoPlayer::EventType::PLAYING) { - _isPlaying = true; - } else { - _isPlaying = false; - } - - if (_eventCallback) + if (event == 1024) { - _eventCallback(this,event); + _fullScreenEnabled = false; + } + else + { + VideoPlayer::EventType videoEvent = (VideoPlayer::EventType)event; + if (videoEvent == VideoPlayer::EventType::PLAYING) { + _isPlaying = true; + } else { + _isPlaying = false; + } + + if (_eventCallback) + { + _eventCallback(this,videoEvent); + } } } @@ -385,7 +388,7 @@ void executeVideoCallback(int index,int event) auto it = s_allVideoPlayers.find(index); if (it != s_allVideoPlayers.end()) { - s_allVideoPlayers[index]->onPlayEvent((VideoPlayer::EventType)event); + s_allVideoPlayers[index]->onPlayEvent(event); } } diff --git a/cocos/ui/UIVideoPlayerIOS.mm b/cocos/ui/UIVideoPlayerIOS.mm index 7bf359f822..7419819baf 100644 --- a/cocos/ui/UIVideoPlayerIOS.mm +++ b/cocos/ui/UIVideoPlayerIOS.mm @@ -449,7 +449,7 @@ void VideoPlayer::addEventListener(const VideoPlayer::ccVideoPlayerCallback& cal _eventCallback = callback; } -void VideoPlayer::onPlayEvent(VideoPlayer::EventType event) +void VideoPlayer::onPlayEvent(int event) { if (event == VideoPlayer::EventType::PLAYING) { _isPlaying = true; @@ -459,7 +459,7 @@ void VideoPlayer::onPlayEvent(VideoPlayer::EventType event) if (_eventCallback) { - _eventCallback(this,event); + _eventCallback(this, (VideoPlayer::EventType)event); } }