Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(493)

Unified Diff: webkit/glue/webmediaplayer_impl.cc

Issue 8570010: Moving media-related files from webkit/glue/ to webkit/media/. (Closed) Base URL: svn://chrome-svn/chrome/trunk/src
Patch Set: minor fixes Created 9 years, 1 month ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
« no previous file with comments | « webkit/glue/webmediaplayer_impl.h ('k') | webkit/glue/webmediaplayer_proxy.h » ('j') | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: webkit/glue/webmediaplayer_impl.cc
diff --git a/webkit/glue/webmediaplayer_impl.cc b/webkit/glue/webmediaplayer_impl.cc
deleted file mode 100644
index 01ddcc06c9191fef3966592df87892058792b880..0000000000000000000000000000000000000000
--- a/webkit/glue/webmediaplayer_impl.cc
+++ /dev/null
@@ -1,877 +0,0 @@
-// Copyright (c) 2011 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#include "webkit/glue/webmediaplayer_impl.h"
-
-#include <limits>
-#include <string>
-
-#include "base/bind.h"
-#include "base/callback.h"
-#include "base/command_line.h"
-#include "base/metrics/histogram.h"
-#include "media/base/composite_data_source_factory.h"
-#include "media/base/filter_collection.h"
-#include "media/base/limits.h"
-#include "media/base/media_log.h"
-#include "media/base/media_switches.h"
-#include "media/base/pipeline_impl.h"
-#include "media/base/video_frame.h"
-#include "media/filters/chunk_demuxer_factory.h"
-#include "media/filters/dummy_demuxer_factory.h"
-#include "media/filters/ffmpeg_audio_decoder.h"
-#include "media/filters/ffmpeg_demuxer_factory.h"
-#include "media/filters/ffmpeg_video_decoder.h"
-#include "media/filters/null_audio_renderer.h"
-#include "third_party/WebKit/Source/WebKit/chromium/public/WebRect.h"
-#include "third_party/WebKit/Source/WebKit/chromium/public/WebSize.h"
-#include "third_party/WebKit/Source/WebKit/chromium/public/WebURL.h"
-#include "third_party/WebKit/Source/WebKit/chromium/public/WebVideoFrame.h"
-#include "third_party/WebKit/Source/WebKit/chromium/public/WebView.h"
-#include "v8/include/v8.h"
-#include "webkit/glue/media/buffered_data_source.h"
-#include "webkit/glue/media/simple_data_source.h"
-#include "webkit/glue/media/media_stream_client.h"
-#include "webkit/glue/media/video_renderer_impl.h"
-#include "webkit/glue/media/web_video_renderer.h"
-#include "webkit/glue/webmediaplayer_delegate.h"
-#include "webkit/glue/webmediaplayer_proxy.h"
-#include "webkit/glue/webvideoframe_impl.h"
-
-using WebKit::WebCanvas;
-using WebKit::WebRect;
-using WebKit::WebSize;
-using media::PipelineStatus;
-
-namespace {
-
-// Amount of extra memory used by each player instance reported to V8.
-// It is not exact number -- first, it differs on different platforms,
-// and second, it is very hard to calculate. Instead, use some arbitrary
-// value that will cause garbage collection from time to time. We don't want
-// it to happen on every allocation, but don't want 5k players to sit in memory
-// either. Looks that chosen constant achieves both goals, at least for audio
-// objects. (Do not worry about video objects yet, JS programs do not create
-// thousands of them...)
-const int kPlayerExtraMemory = 1024 * 1024;
-
-// Limits the range of playback rate.
-//
-// TODO(kylep): Revisit these.
-//
-// Vista has substantially lower performance than XP or Windows7. If you speed
-// up a video too much, it can't keep up, and rendering stops updating except on
-// the time bar. For really high speeds, audio becomes a bottleneck and we just
-// use up the data we have, which may not achieve the speed requested, but will
-// not crash the tab.
-//
-// A very slow speed, ie 0.00000001x, causes the machine to lock up. (It seems
-// like a busy loop). It gets unresponsive, although its not completely dead.
-//
-// Also our timers are not very accurate (especially for ogg), which becomes
-// evident at low speeds and on Vista. Since other speeds are risky and outside
-// the norms, we think 1/16x to 16x is a safe and useful range for now.
-const float kMinRate = 0.0625f;
-const float kMaxRate = 16.0f;
-
-// Platform independent method for converting and rounding floating point
-// seconds to an int64 timestamp.
-//
-// Refer to https://bugs.webkit.org/show_bug.cgi?id=52697 for details.
-base::TimeDelta ConvertSecondsToTimestamp(float seconds) {
- float microseconds = seconds * base::Time::kMicrosecondsPerSecond;
- float integer = ceilf(microseconds);
- float difference = integer - microseconds;
-
- // Round down if difference is large enough.
- if ((microseconds > 0 && difference > 0.5f) ||
- (microseconds <= 0 && difference >= 0.5f)) {
- integer -= 1.0f;
- }
-
- // Now we can safely cast to int64 microseconds.
- return base::TimeDelta::FromMicroseconds(static_cast<int64>(integer));
-}
-
-} // namespace
-
-namespace webkit_glue {
-
-WebMediaPlayerImpl::WebMediaPlayerImpl(
- WebKit::WebMediaPlayerClient* client,
- base::WeakPtr<WebMediaPlayerDelegate> delegate,
- media::FilterCollection* collection,
- media::MessageLoopFactory* message_loop_factory,
- MediaStreamClient* media_stream_client,
- media::MediaLog* media_log)
- : network_state_(WebKit::WebMediaPlayer::Empty),
- ready_state_(WebKit::WebMediaPlayer::HaveNothing),
- main_loop_(NULL),
- filter_collection_(collection),
- pipeline_(NULL),
- message_loop_factory_(message_loop_factory),
- paused_(true),
- seeking_(false),
- playback_rate_(0.0f),
- pending_seek_(false),
- client_(client),
- proxy_(NULL),
- delegate_(delegate),
- media_stream_client_(media_stream_client),
- media_log_(media_log),
- incremented_externally_allocated_memory_(false) {
- // Saves the current message loop.
- DCHECK(!main_loop_);
- main_loop_ = MessageLoop::current();
- media_log_->AddEvent(
- media_log_->CreateEvent(media::MediaLogEvent::WEBMEDIAPLAYER_CREATED));
-}
-
-bool WebMediaPlayerImpl::Initialize(
- WebKit::WebFrame* frame,
- bool use_simple_data_source,
- scoped_refptr<WebVideoRenderer> web_video_renderer) {
- DCHECK_EQ(main_loop_, MessageLoop::current());
- MessageLoop* pipeline_message_loop =
- message_loop_factory_->GetMessageLoop("PipelineThread");
- if (!pipeline_message_loop) {
- NOTREACHED() << "Could not start PipelineThread";
- return false;
- }
-
- // Let V8 know we started new thread if we did not did it yet.
- // Made separate task to avoid deletion of player currently being created.
- // Also, delaying GC until after player starts gets rid of starting lag --
- // collection happens in parallel with playing.
- // TODO(enal): remove when we get rid of per-audio-stream thread.
- if (!incremented_externally_allocated_memory_) {
- MessageLoop::current()->PostTask(
- FROM_HERE,
- base::Bind(&WebMediaPlayerImpl::IncrementExternallyAllocatedMemory,
- AsWeakPtr()));
- }
-
- UMA_HISTOGRAM_BOOLEAN("Media.AcceleratedCompositingActive",
- frame->view()->isAcceleratedCompositingActive());
-
- pipeline_ = new media::PipelineImpl(pipeline_message_loop, media_log_);
-
- // Also we want to be notified of |main_loop_| destruction.
- main_loop_->AddDestructionObserver(this);
-
- // Creates the proxy.
- proxy_ = new WebMediaPlayerProxy(main_loop_, this);
- web_video_renderer->SetWebMediaPlayerProxy(proxy_);
- proxy_->SetVideoRenderer(web_video_renderer);
-
- // Set our pipeline callbacks.
- pipeline_->Init(
- base::Bind(&WebMediaPlayerProxy::PipelineEndedCallback,
- proxy_.get()),
- base::Bind(&WebMediaPlayerProxy::PipelineErrorCallback,
- proxy_.get()),
- base::Bind(&WebMediaPlayerProxy::NetworkEventCallback,
- proxy_.get()));
-
- // A simple data source that keeps all data in memory.
- scoped_ptr<media::DataSourceFactory> simple_data_source_factory(
- SimpleDataSource::CreateFactory(MessageLoop::current(), frame,
- media_log_,
- proxy_->GetBuildObserver()));
-
- // A sophisticated data source that does memory caching.
- scoped_ptr<media::DataSourceFactory> buffered_data_source_factory(
- BufferedDataSource::CreateFactory(MessageLoop::current(), frame,
- media_log_,
- proxy_->GetBuildObserver()));
-
- scoped_ptr<media::CompositeDataSourceFactory> data_source_factory(
- new media::CompositeDataSourceFactory());
-
- if (use_simple_data_source) {
- data_source_factory->AddFactory(simple_data_source_factory.release());
- data_source_factory->AddFactory(buffered_data_source_factory.release());
- } else {
- data_source_factory->AddFactory(buffered_data_source_factory.release());
- data_source_factory->AddFactory(simple_data_source_factory.release());
- }
-
- scoped_ptr<media::DemuxerFactory> demuxer_factory(
- new media::FFmpegDemuxerFactory(data_source_factory.release(),
- pipeline_message_loop));
-
- std::string source_url = GetClient()->sourceURL().spec();
-
- if (!source_url.empty()) {
- demuxer_factory.reset(
- new media::ChunkDemuxerFactory(source_url,
- demuxer_factory.release(),
- proxy_));
- }
- filter_collection_->SetDemuxerFactory(demuxer_factory.release());
-
- // Add in the default filter factories.
- filter_collection_->AddAudioDecoder(new media::FFmpegAudioDecoder(
- message_loop_factory_->GetMessageLoop("AudioDecoderThread")));
- filter_collection_->AddVideoDecoder(new media::FFmpegVideoDecoder(
- message_loop_factory_->GetMessageLoop("VideoDecoderThread")));
- filter_collection_->AddAudioRenderer(new media::NullAudioRenderer());
-
- return true;
-}
-
-WebMediaPlayerImpl::~WebMediaPlayerImpl() {
- DCHECK_EQ(main_loop_, MessageLoop::current());
- Destroy();
- media_log_->AddEvent(
- media_log_->CreateEvent(media::MediaLogEvent::WEBMEDIAPLAYER_DESTROYED));
-
- if (delegate_)
- delegate_->PlayerGone(this);
-
- // Finally tell the |main_loop_| we don't want to be notified of destruction
- // event.
- if (main_loop_) {
- main_loop_->RemoveDestructionObserver(this);
- }
-}
-
-void WebMediaPlayerImpl::load(const WebKit::WebURL& url) {
- DCHECK_EQ(main_loop_, MessageLoop::current());
- DCHECK(proxy_);
-
- if (media_stream_client_) {
- bool has_video = false;
- bool has_audio = false;
- scoped_refptr<media::VideoDecoder> new_decoder =
- media_stream_client_->GetVideoDecoder(url, message_loop_factory_.get());
- if (new_decoder.get()) {
- // Remove the default decoder.
- scoped_refptr<media::VideoDecoder> old_videodecoder;
- filter_collection_->SelectVideoDecoder(&old_videodecoder);
- filter_collection_->AddVideoDecoder(new_decoder.get());
- has_video = true;
- }
-
- // TODO(wjia): add audio decoder handling when it's available.
- if (has_video || has_audio)
- filter_collection_->SetDemuxerFactory(
- new media::DummyDemuxerFactory(has_video, has_audio));
- }
-
- // Handle any volume changes that occured before load().
- setVolume(GetClient()->volume());
- // Get the preload value.
- setPreload(GetClient()->preload());
-
- // Initialize the pipeline.
- SetNetworkState(WebKit::WebMediaPlayer::Loading);
- SetReadyState(WebKit::WebMediaPlayer::HaveNothing);
- pipeline_->Start(
- filter_collection_.release(),
- url.spec(),
- base::Bind(&WebMediaPlayerProxy::PipelineInitializationCallback,
- proxy_.get()));
-
- media_log_->AddEvent(media_log_->CreateLoadEvent(url.spec()));
-}
-
-void WebMediaPlayerImpl::cancelLoad() {
- DCHECK_EQ(main_loop_, MessageLoop::current());
-}
-
-void WebMediaPlayerImpl::play() {
- DCHECK_EQ(main_loop_, MessageLoop::current());
-
- paused_ = false;
- pipeline_->SetPlaybackRate(playback_rate_);
-
- media_log_->AddEvent(media_log_->CreateEvent(media::MediaLogEvent::PLAY));
-
- if (delegate_)
- delegate_->DidPlay(this);
-}
-
-void WebMediaPlayerImpl::pause() {
- DCHECK_EQ(main_loop_, MessageLoop::current());
-
- paused_ = true;
- pipeline_->SetPlaybackRate(0.0f);
- paused_time_ = pipeline_->GetCurrentTime();
-
- media_log_->AddEvent(media_log_->CreateEvent(media::MediaLogEvent::PAUSE));
-
- if (delegate_)
- delegate_->DidPause(this);
-}
-
-bool WebMediaPlayerImpl::supportsFullscreen() const {
- DCHECK_EQ(main_loop_, MessageLoop::current());
- return true;
-}
-
-bool WebMediaPlayerImpl::supportsSave() const {
- DCHECK_EQ(main_loop_, MessageLoop::current());
- return true;
-}
-
-void WebMediaPlayerImpl::seek(float seconds) {
- DCHECK_EQ(main_loop_, MessageLoop::current());
-
- // WebKit fires a seek(0) at the very start, however pipeline already does a
- // seek(0) internally. Avoid doing seek(0) the second time because this will
- // cause extra pre-rolling and will break servers without range request
- // support.
- //
- // We still have to notify WebKit that time has changed otherwise
- // HTMLMediaElement gets into an inconsistent state.
- if (pipeline_->GetCurrentTime().ToInternalValue() == 0 && seconds == 0) {
- GetClient()->timeChanged();
- return;
- }
-
- if (seeking_) {
- pending_seek_ = true;
- pending_seek_seconds_ = seconds;
- return;
- }
-
- media_log_->AddEvent(media_log_->CreateSeekEvent(seconds));
-
- base::TimeDelta seek_time = ConvertSecondsToTimestamp(seconds);
-
- // Update our paused time.
- if (paused_) {
- paused_time_ = seek_time;
- }
-
- seeking_ = true;
-
- proxy_->DemuxerFlush();
-
- // Kick off the asynchronous seek!
- pipeline_->Seek(
- seek_time,
- base::Bind(&WebMediaPlayerProxy::PipelineSeekCallback,
- proxy_.get()));
-}
-
-void WebMediaPlayerImpl::setEndTime(float seconds) {
- DCHECK_EQ(main_loop_, MessageLoop::current());
-
- // TODO(hclam): add method call when it has been implemented.
- return;
-}
-
-void WebMediaPlayerImpl::setRate(float rate) {
- DCHECK_EQ(main_loop_, MessageLoop::current());
-
- // TODO(kylep): Remove when support for negatives is added. Also, modify the
- // following checks so rewind uses reasonable values also.
- if (rate < 0.0f)
- return;
-
- // Limit rates to reasonable values by clamping.
- if (rate != 0.0f) {
- if (rate < kMinRate)
- rate = kMinRate;
- else if (rate > kMaxRate)
- rate = kMaxRate;
- }
-
- playback_rate_ = rate;
- if (!paused_) {
- pipeline_->SetPlaybackRate(rate);
- }
-}
-
-void WebMediaPlayerImpl::setVolume(float volume) {
- DCHECK_EQ(main_loop_, MessageLoop::current());
-
- pipeline_->SetVolume(volume);
-}
-
-void WebMediaPlayerImpl::setVisible(bool visible) {
- DCHECK_EQ(main_loop_, MessageLoop::current());
-
- // TODO(hclam): add appropriate method call when pipeline has it implemented.
- return;
-}
-
-#define COMPILE_ASSERT_MATCHING_ENUM(webkit_name, chromium_name) \
- COMPILE_ASSERT(static_cast<int>(WebKit::WebMediaPlayer::webkit_name) == \
- static_cast<int>(media::chromium_name), \
- mismatching_enums)
-COMPILE_ASSERT_MATCHING_ENUM(None, NONE);
-COMPILE_ASSERT_MATCHING_ENUM(MetaData, METADATA);
-COMPILE_ASSERT_MATCHING_ENUM(Auto, AUTO);
-
-void WebMediaPlayerImpl::setPreload(WebKit::WebMediaPlayer::Preload preload) {
- DCHECK_EQ(main_loop_, MessageLoop::current());
-
- pipeline_->SetPreload(static_cast<media::Preload>(preload));
-}
-
-bool WebMediaPlayerImpl::totalBytesKnown() {
- DCHECK_EQ(main_loop_, MessageLoop::current());
-
- return pipeline_->GetTotalBytes() != 0;
-}
-
-bool WebMediaPlayerImpl::hasVideo() const {
- DCHECK_EQ(main_loop_, MessageLoop::current());
-
- return pipeline_->HasVideo();
-}
-
-bool WebMediaPlayerImpl::hasAudio() const {
- DCHECK_EQ(main_loop_, MessageLoop::current());
-
- return pipeline_->HasAudio();
-}
-
-WebKit::WebSize WebMediaPlayerImpl::naturalSize() const {
- DCHECK_EQ(main_loop_, MessageLoop::current());
-
- gfx::Size size;
- pipeline_->GetNaturalVideoSize(&size);
- return WebKit::WebSize(size);
-}
-
-bool WebMediaPlayerImpl::paused() const {
- DCHECK_EQ(main_loop_, MessageLoop::current());
-
- return pipeline_->GetPlaybackRate() == 0.0f;
-}
-
-bool WebMediaPlayerImpl::seeking() const {
- DCHECK_EQ(main_loop_, MessageLoop::current());
-
- if (ready_state_ == WebKit::WebMediaPlayer::HaveNothing)
- return false;
-
- return seeking_;
-}
-
-float WebMediaPlayerImpl::duration() const {
- DCHECK_EQ(main_loop_, MessageLoop::current());
-
- base::TimeDelta duration = pipeline_->GetMediaDuration();
- if (duration.InMicroseconds() == media::Limits::kMaxTimeInMicroseconds)
- return std::numeric_limits<float>::infinity();
- return static_cast<float>(duration.InSecondsF());
-}
-
-float WebMediaPlayerImpl::currentTime() const {
- DCHECK_EQ(main_loop_, MessageLoop::current());
- if (paused_) {
- return static_cast<float>(paused_time_.InSecondsF());
- }
- return static_cast<float>(pipeline_->GetCurrentTime().InSecondsF());
-}
-
-int WebMediaPlayerImpl::dataRate() const {
- DCHECK_EQ(main_loop_, MessageLoop::current());
-
- // TODO(hclam): Add this method call if pipeline has it in the interface.
- return 0;
-}
-
-WebKit::WebMediaPlayer::NetworkState WebMediaPlayerImpl::networkState() const {
- return network_state_;
-}
-
-WebKit::WebMediaPlayer::ReadyState WebMediaPlayerImpl::readyState() const {
- return ready_state_;
-}
-
-const WebKit::WebTimeRanges& WebMediaPlayerImpl::buffered() {
- DCHECK_EQ(main_loop_, MessageLoop::current());
-
- // Update buffered_ with the most recent buffered time.
- if (buffered_.size() > 0) {
- float buffered_time = static_cast<float>(
- pipeline_->GetBufferedTime().InSecondsF());
- if (buffered_time >= buffered_[0].start)
- buffered_[0].end = buffered_time;
- }
-
- return buffered_;
-}
-
-float WebMediaPlayerImpl::maxTimeSeekable() const {
- DCHECK_EQ(main_loop_, MessageLoop::current());
-
- // If we are performing streaming, we report that we cannot seek at all.
- // We are using this flag to indicate if the data source supports seeking
- // or not. We should be able to seek even if we are performing streaming.
- // TODO(hclam): We need to update this when we have better caching.
- if (pipeline_->IsStreaming())
- return 0.0f;
- return static_cast<float>(pipeline_->GetMediaDuration().InSecondsF());
-}
-
-unsigned long long WebMediaPlayerImpl::bytesLoaded() const {
- DCHECK_EQ(main_loop_, MessageLoop::current());
-
- return pipeline_->GetBufferedBytes();
-}
-
-unsigned long long WebMediaPlayerImpl::totalBytes() const {
- DCHECK_EQ(main_loop_, MessageLoop::current());
-
- return pipeline_->GetTotalBytes();
-}
-
-void WebMediaPlayerImpl::setSize(const WebSize& size) {
- DCHECK_EQ(main_loop_, MessageLoop::current());
- DCHECK(proxy_);
-
- proxy_->SetSize(gfx::Rect(0, 0, size.width, size.height));
-}
-
-void WebMediaPlayerImpl::paint(WebCanvas* canvas,
- const WebRect& rect) {
- DCHECK_EQ(main_loop_, MessageLoop::current());
- DCHECK(proxy_);
-
-#if WEBKIT_USING_SKIA
- proxy_->Paint(canvas, rect);
-#elif WEBKIT_USING_CG
- // Get the current scaling in X and Y.
- CGAffineTransform mat = CGContextGetCTM(canvas);
- float scale_x = sqrt(mat.a * mat.a + mat.b * mat.b);
- float scale_y = sqrt(mat.c * mat.c + mat.d * mat.d);
- float inverse_scale_x = SkScalarNearlyZero(scale_x) ? 0.0f : 1.0f / scale_x;
- float inverse_scale_y = SkScalarNearlyZero(scale_y) ? 0.0f : 1.0f / scale_y;
- int scaled_width = static_cast<int>(rect.width * fabs(scale_x));
- int scaled_height = static_cast<int>(rect.height * fabs(scale_y));
-
- // Make sure we don't create a huge canvas.
- // TODO(hclam): Respect the aspect ratio.
- if (scaled_width > static_cast<int>(media::Limits::kMaxCanvas))
- scaled_width = media::Limits::kMaxCanvas;
- if (scaled_height > static_cast<int>(media::Limits::kMaxCanvas))
- scaled_height = media::Limits::kMaxCanvas;
-
- // If there is no preexisting platform canvas, or if the size has
- // changed, recreate the canvas. This is to avoid recreating the bitmap
- // buffer over and over for each frame of video.
- if (!skia_canvas_.get() ||
- skia_canvas_->getDevice()->width() != scaled_width ||
- skia_canvas_->getDevice()->height() != scaled_height) {
- skia_canvas_.reset(
- new skia::PlatformCanvas(scaled_width, scaled_height, true));
- }
-
- // Draw to our temporary skia canvas.
- gfx::Rect normalized_rect(scaled_width, scaled_height);
- proxy_->Paint(skia_canvas_.get(), normalized_rect);
-
- // The mac coordinate system is flipped vertical from the normal skia
- // coordinates. During painting of the frame, flip the coordinates
- // system and, for simplicity, also translate the clip rectangle to
- // start at 0,0.
- CGContextSaveGState(canvas);
- CGContextTranslateCTM(canvas, rect.x, rect.height + rect.y);
- CGContextScaleCTM(canvas, inverse_scale_x, -inverse_scale_y);
-
- // We need a local variable CGRect version for DrawToContext.
- CGRect normalized_cgrect =
- CGRectMake(normalized_rect.x(), normalized_rect.y(),
- normalized_rect.width(), normalized_rect.height());
-
- // Copy the frame rendered to our temporary skia canvas onto the passed in
- // canvas.
- skia::DrawToNativeContext(skia_canvas_.get(), canvas, 0, 0,
- &normalized_cgrect);
-
- CGContextRestoreGState(canvas);
-#else
- NOTIMPLEMENTED() << "We only support rendering to skia or CG";
-#endif
-}
-
-bool WebMediaPlayerImpl::hasSingleSecurityOrigin() const {
- if (proxy_)
- return proxy_->HasSingleOrigin();
- return true;
-}
-
-WebKit::WebMediaPlayer::MovieLoadType
- WebMediaPlayerImpl::movieLoadType() const {
- DCHECK_EQ(main_loop_, MessageLoop::current());
-
- // TODO(hclam): If the pipeline is performing streaming, we say that this is
- // a live stream. But instead it should be a StoredStream if we have proper
- // caching.
- if (pipeline_->IsStreaming())
- return WebKit::WebMediaPlayer::LiveStream;
- return WebKit::WebMediaPlayer::Unknown;
-}
-
-float WebMediaPlayerImpl::mediaTimeForTimeValue(float timeValue) const {
- return ConvertSecondsToTimestamp(timeValue).InSecondsF();
-}
-
-unsigned WebMediaPlayerImpl::decodedFrameCount() const {
- DCHECK_EQ(main_loop_, MessageLoop::current());
-
- media::PipelineStatistics stats = pipeline_->GetStatistics();
- return stats.video_frames_decoded;
-}
-
-unsigned WebMediaPlayerImpl::droppedFrameCount() const {
- DCHECK_EQ(main_loop_, MessageLoop::current());
-
- media::PipelineStatistics stats = pipeline_->GetStatistics();
- return stats.video_frames_dropped;
-}
-
-unsigned WebMediaPlayerImpl::audioDecodedByteCount() const {
- DCHECK_EQ(main_loop_, MessageLoop::current());
-
- media::PipelineStatistics stats = pipeline_->GetStatistics();
- return stats.audio_bytes_decoded;
-}
-
-unsigned WebMediaPlayerImpl::videoDecodedByteCount() const {
- DCHECK_EQ(main_loop_, MessageLoop::current());
-
- media::PipelineStatistics stats = pipeline_->GetStatistics();
- return stats.video_bytes_decoded;
-}
-
-WebKit::WebVideoFrame* WebMediaPlayerImpl::getCurrentFrame() {
- scoped_refptr<media::VideoFrame> video_frame;
- proxy_->GetCurrentFrame(&video_frame);
- if (video_frame.get())
- return new WebVideoFrameImpl(video_frame);
- return NULL;
-}
-
-void WebMediaPlayerImpl::putCurrentFrame(
- WebKit::WebVideoFrame* web_video_frame) {
- if (web_video_frame) {
- scoped_refptr<media::VideoFrame> video_frame(
- WebVideoFrameImpl::toVideoFrame(web_video_frame));
- proxy_->PutCurrentFrame(video_frame);
- delete web_video_frame;
- }
-}
-
-bool WebMediaPlayerImpl::sourceAppend(const unsigned char* data,
- unsigned length) {
- DCHECK_EQ(main_loop_, MessageLoop::current());
- return proxy_->DemuxerAppend(data, length);
-}
-
-void WebMediaPlayerImpl::sourceEndOfStream(
- WebKit::WebMediaPlayer::EndOfStreamStatus status) {
- DCHECK_EQ(main_loop_, MessageLoop::current());
- media::PipelineStatus pipeline_status = media::PIPELINE_OK;
-
- switch(status) {
- case WebKit::WebMediaPlayer::EosNoError:
- break;
- case WebKit::WebMediaPlayer::EosNetworkError:
- pipeline_status = media::PIPELINE_ERROR_NETWORK;
- break;
- case WebKit::WebMediaPlayer::EosDecodeError:
- pipeline_status = media::PIPELINE_ERROR_DECODE;
- break;
- default:
- NOTIMPLEMENTED();
- }
-
- proxy_->DemuxerEndOfStream(pipeline_status);
-}
-
-void WebMediaPlayerImpl::WillDestroyCurrentMessageLoop() {
- Destroy();
- main_loop_ = NULL;
-}
-
-void WebMediaPlayerImpl::Repaint() {
- DCHECK_EQ(main_loop_, MessageLoop::current());
- GetClient()->repaint();
-}
-
-void WebMediaPlayerImpl::OnPipelineInitialize(PipelineStatus status) {
- DCHECK_EQ(main_loop_, MessageLoop::current());
- if (status == media::PIPELINE_OK) {
- // Only keep one time range starting from 0.
- WebKit::WebTimeRanges new_buffered(static_cast<size_t>(1));
- new_buffered[0].start = 0.0f;
- new_buffered[0].end =
- static_cast<float>(pipeline_->GetMediaDuration().InSecondsF());
- buffered_.swap(new_buffered);
-
- if (pipeline_->IsLoaded()) {
- SetNetworkState(WebKit::WebMediaPlayer::Loaded);
- }
-
- // Since we have initialized the pipeline, say we have everything otherwise
- // we'll remain either loading/idle.
- // TODO(hclam): change this to report the correct status.
- SetReadyState(WebKit::WebMediaPlayer::HaveMetadata);
- SetReadyState(WebKit::WebMediaPlayer::HaveEnoughData);
- } else {
- // TODO(hclam): should use |status| to determine the state
- // properly and reports error using MediaError.
- // WebKit uses FormatError to indicate an error for bogus URL or bad file.
- // Since we are at the initialization stage we can safely treat every error
- // as format error. Should post a task to call to |webmediaplayer_|.
- SetNetworkState(WebKit::WebMediaPlayer::FormatError);
- }
-
- // Repaint to trigger UI update.
- Repaint();
-}
-
-void WebMediaPlayerImpl::OnPipelineSeek(PipelineStatus status) {
- DCHECK_EQ(main_loop_, MessageLoop::current());
- seeking_ = false;
- if (pending_seek_) {
- pending_seek_ = false;
- seek(pending_seek_seconds_);
- return;
- }
-
- if (status == media::PIPELINE_OK) {
- // Update our paused time.
- if (paused_) {
- paused_time_ = pipeline_->GetCurrentTime();
- }
-
- SetReadyState(WebKit::WebMediaPlayer::HaveEnoughData);
- GetClient()->timeChanged();
- }
-}
-
-void WebMediaPlayerImpl::OnPipelineEnded(PipelineStatus status) {
- DCHECK_EQ(main_loop_, MessageLoop::current());
- if (status == media::PIPELINE_OK) {
- GetClient()->timeChanged();
- }
-}
-
-void WebMediaPlayerImpl::OnPipelineError(PipelineStatus error) {
- DCHECK_EQ(main_loop_, MessageLoop::current());
- switch (error) {
- case media::PIPELINE_OK:
- LOG(DFATAL) << "PIPELINE_OK isn't an error!";
- break;
-
- case media::PIPELINE_ERROR_NETWORK:
- SetNetworkState(WebMediaPlayer::NetworkError);
- break;
-
- case media::PIPELINE_ERROR_INITIALIZATION_FAILED:
- case media::PIPELINE_ERROR_REQUIRED_FILTER_MISSING:
- case media::PIPELINE_ERROR_COULD_NOT_RENDER:
- case media::PIPELINE_ERROR_URL_NOT_FOUND:
- case media::PIPELINE_ERROR_READ:
- case media::DEMUXER_ERROR_COULD_NOT_OPEN:
- case media::DEMUXER_ERROR_COULD_NOT_PARSE:
- case media::DEMUXER_ERROR_NO_SUPPORTED_STREAMS:
- case media::DEMUXER_ERROR_COULD_NOT_CREATE_THREAD:
- case media::DECODER_ERROR_NOT_SUPPORTED:
- case media::DATASOURCE_ERROR_URL_NOT_SUPPORTED:
- // Format error.
- SetNetworkState(WebMediaPlayer::FormatError);
- break;
-
- case media::PIPELINE_ERROR_DECODE:
- case media::PIPELINE_ERROR_ABORT:
- case media::PIPELINE_ERROR_OUT_OF_MEMORY:
- case media::PIPELINE_ERROR_AUDIO_HARDWARE:
- case media::PIPELINE_ERROR_OPERATION_PENDING:
- case media::PIPELINE_ERROR_INVALID_STATE:
- // Decode error.
- SetNetworkState(WebMediaPlayer::DecodeError);
- break;
- }
-
- // Repaint to trigger UI update.
- Repaint();
-}
-
-void WebMediaPlayerImpl::OnNetworkEvent(bool is_downloading_data) {
- DCHECK_EQ(main_loop_, MessageLoop::current());
- if (is_downloading_data)
- SetNetworkState(WebKit::WebMediaPlayer::Loading);
- else
- SetNetworkState(WebKit::WebMediaPlayer::Idle);
-}
-
-void WebMediaPlayerImpl::OnDemuxerOpened() {
- DCHECK_EQ(main_loop_, MessageLoop::current());
-
- GetClient()->sourceOpened();
-}
-
-void WebMediaPlayerImpl::SetNetworkState(
- WebKit::WebMediaPlayer::NetworkState state) {
- DCHECK_EQ(main_loop_, MessageLoop::current());
- // Always notify to ensure client has the latest value.
- network_state_ = state;
- GetClient()->networkStateChanged();
-}
-
-void WebMediaPlayerImpl::SetReadyState(
- WebKit::WebMediaPlayer::ReadyState state) {
- DCHECK_EQ(main_loop_, MessageLoop::current());
- // Always notify to ensure client has the latest value.
- ready_state_ = state;
- GetClient()->readyStateChanged();
-}
-
-void WebMediaPlayerImpl::Destroy() {
- DCHECK_EQ(main_loop_, MessageLoop::current());
-
- // Tell the data source to abort any pending reads so that the pipeline is
- // not blocked when issuing stop commands to the other filters.
- if (proxy_) {
- proxy_->AbortDataSources();
- proxy_->DemuxerShutdown();
- }
-
- // Make sure to kill the pipeline so there's no more media threads running.
- // Note: stopping the pipeline might block for a long time.
- if (pipeline_) {
- media::PipelineStatusNotification note;
- pipeline_->Stop(note.Callback());
- note.Wait();
-
- // Let V8 know we are not using extra resources anymore.
- if (incremented_externally_allocated_memory_) {
- v8::V8::AdjustAmountOfExternalAllocatedMemory(-kPlayerExtraMemory);
- incremented_externally_allocated_memory_ = false;
- }
- }
-
- message_loop_factory_.reset();
-
- // And then detach the proxy, it may live on the render thread for a little
- // longer until all the tasks are finished.
- if (proxy_) {
- proxy_->Detach();
- proxy_ = NULL;
- }
-}
-
-WebKit::WebMediaPlayerClient* WebMediaPlayerImpl::GetClient() {
- DCHECK_EQ(main_loop_, MessageLoop::current());
- DCHECK(client_);
- return client_;
-}
-
-void WebMediaPlayerImpl::IncrementExternallyAllocatedMemory() {
- DCHECK_EQ(main_loop_, MessageLoop::current());
- incremented_externally_allocated_memory_ = true;
- v8::V8::AdjustAmountOfExternalAllocatedMemory(kPlayerExtraMemory);
-}
-
-} // namespace webkit_glue
« no previous file with comments | « webkit/glue/webmediaplayer_impl.h ('k') | webkit/glue/webmediaplayer_proxy.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698