content_video_view.cc revision 010d83a9304c5a91596085d917d248abff47903a
1// Copyright (c) 2012 The Chromium Authors. All rights reserved. 2// Use of this source code is governed by a BSD-style license that can be 3// found in the LICENSE file. 4 5#include "content/browser/android/content_video_view.h" 6 7#include "base/command_line.h" 8#include "base/logging.h" 9#include "base/message_loop/message_loop.h" 10#include "content/browser/android/content_view_core_impl.h" 11#include "content/browser/media/android/browser_media_player_manager.h" 12#include "content/browser/power_save_blocker_impl.h" 13#include "content/common/android/surface_texture_peer.h" 14#include "content/public/common/content_switches.h" 15#include "jni/ContentVideoView_jni.h" 16 17using base::android::AttachCurrentThread; 18using base::android::CheckException; 19using base::android::ScopedJavaGlobalRef; 20 21namespace content { 22 23namespace { 24// There can only be one content video view at a time, this holds onto that 25// singleton instance. 26ContentVideoView* g_content_video_view = NULL; 27 28} // namespace 29 30static jobject GetSingletonJavaContentVideoView(JNIEnv*env, jclass) { 31 if (g_content_video_view) 32 return g_content_video_view->GetJavaObject(env).Release(); 33 else 34 return NULL; 35} 36 37bool ContentVideoView::RegisterContentVideoView(JNIEnv* env) { 38 return RegisterNativesImpl(env); 39} 40 41ContentVideoView* ContentVideoView::GetInstance() { 42 return g_content_video_view; 43} 44 45ContentVideoView::ContentVideoView( 46 BrowserMediaPlayerManager* manager) 47 : manager_(manager), 48 weak_factory_(this) { 49 DCHECK(!g_content_video_view); 50 j_content_video_view_ = CreateJavaObject(); 51 g_content_video_view = this; 52 CreatePowerSaveBlocker(); 53} 54 55ContentVideoView::~ContentVideoView() { 56 DCHECK(g_content_video_view); 57 JNIEnv* env = AttachCurrentThread(); 58 ScopedJavaLocalRef<jobject> content_video_view = GetJavaObject(env); 59 if (!content_video_view.is_null()) { 60 Java_ContentVideoView_destroyContentVideoView(env, 61 content_video_view.obj(), true); 62 j_content_video_view_.reset(); 63 } 64 g_content_video_view = NULL; 65} 66 67void ContentVideoView::OpenVideo() { 68 JNIEnv* env = AttachCurrentThread(); 69 ScopedJavaLocalRef<jobject> content_video_view = GetJavaObject(env); 70 if (!content_video_view.is_null()) { 71 CreatePowerSaveBlocker(); 72 Java_ContentVideoView_openVideo(env, content_video_view.obj()); 73 } 74} 75 76void ContentVideoView::OnMediaPlayerError(int error_type) { 77 JNIEnv* env = AttachCurrentThread(); 78 ScopedJavaLocalRef<jobject> content_video_view = GetJavaObject(env); 79 if (!content_video_view.is_null()) { 80 power_save_blocker_.reset(); 81 Java_ContentVideoView_onMediaPlayerError(env, content_video_view.obj(), 82 error_type); 83 } 84} 85 86void ContentVideoView::OnVideoSizeChanged(int width, int height) { 87 JNIEnv* env = AttachCurrentThread(); 88 ScopedJavaLocalRef<jobject> content_video_view = GetJavaObject(env); 89 if (!content_video_view.is_null()) { 90 Java_ContentVideoView_onVideoSizeChanged(env, content_video_view.obj(), 91 width, height); 92 } 93} 94 95void ContentVideoView::OnBufferingUpdate(int percent) { 96 JNIEnv* env = AttachCurrentThread(); 97 ScopedJavaLocalRef<jobject> content_video_view = GetJavaObject(env); 98 if (!content_video_view.is_null()) { 99 Java_ContentVideoView_onBufferingUpdate(env, content_video_view.obj(), 100 percent); 101 } 102} 103 104void ContentVideoView::OnPlaybackComplete() { 105 JNIEnv* env = AttachCurrentThread(); 106 ScopedJavaLocalRef<jobject> content_video_view = GetJavaObject(env); 107 if (!content_video_view.is_null()) { 108 power_save_blocker_.reset(); 109 Java_ContentVideoView_onPlaybackComplete(env, content_video_view.obj()); 110 } 111} 112 113void ContentVideoView::OnExitFullscreen() { 114 JNIEnv* env = AttachCurrentThread(); 115 ScopedJavaLocalRef<jobject> content_video_view = GetJavaObject(env); 116 if (!content_video_view.is_null()) 117 Java_ContentVideoView_onExitFullscreen(env, content_video_view.obj()); 118} 119 120void ContentVideoView::UpdateMediaMetadata() { 121 JNIEnv* env = AttachCurrentThread(); 122 ScopedJavaLocalRef<jobject> content_video_view = GetJavaObject(env); 123 if (content_video_view.is_null()) 124 return; 125 126 media::MediaPlayerAndroid* player = manager_->GetFullscreenPlayer(); 127 if (player && player->IsPlayerReady()) { 128 Java_ContentVideoView_onUpdateMediaMetadata( 129 env, content_video_view.obj(), player->GetVideoWidth(), 130 player->GetVideoHeight(), 131 static_cast<int>(player->GetDuration().InMilliseconds()), 132 player->CanPause(),player->CanSeekForward(), player->CanSeekBackward()); 133 } 134} 135 136int ContentVideoView::GetVideoWidth(JNIEnv*, jobject obj) const { 137 media::MediaPlayerAndroid* player = manager_->GetFullscreenPlayer(); 138 return player ? player->GetVideoWidth() : 0; 139} 140 141int ContentVideoView::GetVideoHeight(JNIEnv*, jobject obj) const { 142 media::MediaPlayerAndroid* player = manager_->GetFullscreenPlayer(); 143 return player ? player->GetVideoHeight() : 0; 144} 145 146int ContentVideoView::GetDurationInMilliSeconds(JNIEnv*, jobject obj) const { 147 media::MediaPlayerAndroid* player = manager_->GetFullscreenPlayer(); 148 return player ? player->GetDuration().InMilliseconds() : -1; 149} 150 151int ContentVideoView::GetCurrentPosition(JNIEnv*, jobject obj) const { 152 media::MediaPlayerAndroid* player = manager_->GetFullscreenPlayer(); 153 return player ? player->GetCurrentTime().InMilliseconds() : 0; 154} 155 156bool ContentVideoView::IsPlaying(JNIEnv*, jobject obj) { 157 media::MediaPlayerAndroid* player = manager_->GetFullscreenPlayer(); 158 return player ? player->IsPlaying() : false; 159} 160 161void ContentVideoView::SeekTo(JNIEnv*, jobject obj, jint msec) { 162 manager_->FullscreenPlayerSeek(msec); 163} 164 165void ContentVideoView::Play(JNIEnv*, jobject obj) { 166 CreatePowerSaveBlocker(); 167 manager_->FullscreenPlayerPlay(); 168} 169 170void ContentVideoView::Pause(JNIEnv*, jobject obj) { 171 power_save_blocker_.reset(); 172 manager_->FullscreenPlayerPause(); 173} 174 175void ContentVideoView::ExitFullscreen( 176 JNIEnv*, jobject, jboolean release_media_player) { 177 power_save_blocker_.reset(); 178 j_content_video_view_.reset(); 179 manager_->ExitFullscreen(release_media_player); 180} 181 182void ContentVideoView::SetSurface(JNIEnv* env, jobject obj, 183 jobject surface) { 184 manager_->SetVideoSurface( 185 gfx::ScopedJavaSurface::AcquireExternalSurface(surface)); 186} 187 188void ContentVideoView::RequestMediaMetadata(JNIEnv* env, jobject obj) { 189 base::MessageLoop::current()->PostTask( 190 FROM_HERE, 191 base::Bind(&ContentVideoView::UpdateMediaMetadata, 192 weak_factory_.GetWeakPtr())); 193} 194 195ScopedJavaLocalRef<jobject> ContentVideoView::GetJavaObject(JNIEnv* env) { 196 return j_content_video_view_.get(env); 197} 198 199gfx::NativeView ContentVideoView::GetNativeView() { 200 JNIEnv* env = AttachCurrentThread(); 201 ScopedJavaLocalRef<jobject> content_video_view = GetJavaObject(env); 202 if (content_video_view.is_null()) 203 return NULL; 204 205 return reinterpret_cast<gfx::NativeView>( 206 Java_ContentVideoView_getNativeViewAndroid(env, 207 content_video_view.obj())); 208 209} 210 211JavaObjectWeakGlobalRef ContentVideoView::CreateJavaObject() { 212 ContentViewCoreImpl* content_view_core = manager_->GetContentViewCore(); 213 JNIEnv* env = AttachCurrentThread(); 214 bool legacyMode = CommandLine::ForCurrentProcess()->HasSwitch( 215 switches::kDisableOverlayFullscreenVideoSubtitle); 216 return JavaObjectWeakGlobalRef( 217 env, 218 Java_ContentVideoView_createContentVideoView( 219 env, 220 content_view_core->GetContext().obj(), 221 reinterpret_cast<intptr_t>(this), 222 content_view_core->GetContentVideoViewClient().obj(), 223 legacyMode).obj()); 224} 225 226void ContentVideoView::CreatePowerSaveBlocker() { 227 if (!CommandLine::ForCurrentProcess()->HasSwitch( 228 switches::kDisableOverlayFullscreenVideoSubtitle)) { 229 return; 230 } 231 232 if (power_save_blocker_) return; 233 234 power_save_blocker_ = PowerSaveBlocker::Create( 235 PowerSaveBlocker::kPowerSaveBlockPreventDisplaySleep, 236 "Playing video").Pass(); 237 static_cast<PowerSaveBlockerImpl*>(power_save_blocker_.get())-> 238 InitDisplaySleepBlocker(GetNativeView()); 239} 240} // namespace content 241