When Retrier succeeds, record errors it encountered.
[chromium-blink-merge.git] / webkit / media / webmediaplayer_impl.h
blob68390504d82342e6f00477eb44c83a58ac00a8ef
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.
5 // Delegate calls from WebCore::MediaPlayerPrivate to Chrome's video player.
6 // It contains Pipeline which is the actual media player pipeline, it glues
7 // the media player pipeline, data source, audio renderer and renderer.
8 // Pipeline would creates multiple threads and access some public methods
9 // of this class, so we need to be extra careful about concurrent access of
10 // methods and members.
12 // Other issues:
13 // During tear down of the whole browser or a tab, the DOM tree may not be
14 // destructed nicely, and there will be some dangling media threads trying to
15 // the main thread, so we need this class to listen to destruction event of the
16 // main thread and cleanup the media threads when the even is received. Also
17 // at destruction of this class we will need to unhook it from destruction event
18 // list of the main thread.
20 #ifndef WEBKIT_MEDIA_WEBMEDIAPLAYER_IMPL_H_
21 #define WEBKIT_MEDIA_WEBMEDIAPLAYER_IMPL_H_
23 #include <string>
25 #include "base/memory/ref_counted.h"
26 #include "base/memory/scoped_ptr.h"
27 #include "base/memory/weak_ptr.h"
28 #include "base/threading/thread.h"
29 #include "cc/layers/video_frame_provider.h"
30 #include "googleurl/src/gurl.h"
31 #include "media/base/audio_renderer_sink.h"
32 #include "media/base/decryptor.h"
33 #include "media/base/pipeline.h"
34 #include "media/filters/gpu_video_decoder.h"
35 #include "media/filters/skcanvas_video_renderer.h"
36 #include "skia/ext/platform_canvas.h"
37 #include "third_party/WebKit/Source/Platform/chromium/public/WebGraphicsContext3D.h"
38 #include "third_party/WebKit/Source/WebKit/chromium/public/WebAudioSourceProvider.h"
39 #include "third_party/WebKit/Source/WebKit/chromium/public/WebMediaPlayer.h"
40 #include "third_party/WebKit/Source/WebKit/chromium/public/WebMediaPlayerClient.h"
41 #include "webkit/media/crypto/key_systems.h"
42 #include "webkit/media/crypto/proxy_decryptor.h"
44 class RenderAudioSourceProvider;
46 namespace WebKit {
47 class WebFrame;
50 namespace base {
51 class MessageLoopProxy;
54 namespace media {
55 class ChunkDemuxer;
56 class FFmpegDemuxer;
57 class MediaLog;
60 namespace webkit {
61 class WebLayerImpl;
64 namespace webkit_media {
66 class BufferedDataSource;
67 class MediaStreamClient;
68 class WebAudioSourceProviderImpl;
69 class WebMediaPlayerDelegate;
70 class WebMediaPlayerParams;
72 class WebMediaPlayerImpl
73 : public WebKit::WebMediaPlayer,
74 public cc::VideoFrameProvider,
75 public base::MessageLoop::DestructionObserver,
76 public base::SupportsWeakPtr<WebMediaPlayerImpl> {
77 public:
78 // Constructs a WebMediaPlayer implementation using Chromium's media stack.
80 // |delegate| may be null.
81 WebMediaPlayerImpl(
82 WebKit::WebFrame* frame,
83 WebKit::WebMediaPlayerClient* client,
84 base::WeakPtr<WebMediaPlayerDelegate> delegate,
85 const WebMediaPlayerParams& params);
86 virtual ~WebMediaPlayerImpl();
88 virtual void load(const WebKit::WebURL& url, CORSMode cors_mode);
89 virtual void load(const WebKit::WebURL& url,
90 WebKit::WebMediaSource* media_source,
91 CORSMode cors_mode);
92 virtual void cancelLoad();
94 // Playback controls.
95 virtual void play();
96 virtual void pause();
97 virtual bool supportsFullscreen() const;
98 virtual bool supportsSave() const;
99 virtual void seek(double seconds);
100 virtual void setRate(double rate);
101 virtual void setVolume(double volume);
102 virtual void setVisible(bool visible);
103 virtual void setPreload(WebKit::WebMediaPlayer::Preload preload);
104 virtual bool totalBytesKnown();
105 virtual const WebKit::WebTimeRanges& buffered();
106 virtual double maxTimeSeekable() const;
108 // Methods for painting.
109 virtual void setSize(const WebKit::WebSize& size);
111 virtual void paint(WebKit::WebCanvas* canvas,
112 const WebKit::WebRect& rect,
113 uint8_t alpha);
115 // True if the loaded media has a playable video/audio track.
116 virtual bool hasVideo() const;
117 virtual bool hasAudio() const;
119 // Dimensions of the video.
120 virtual WebKit::WebSize naturalSize() const;
122 // Getters of playback state.
123 virtual bool paused() const;
124 virtual bool seeking() const;
125 virtual double duration() const;
126 virtual double currentTime() const;
128 // Get rate of loading the resource.
129 virtual int32 dataRate() const;
131 // Internal states of loading and network.
132 // TODO(hclam): Ask the pipeline about the state rather than having reading
133 // them from members which would cause race conditions.
134 virtual WebKit::WebMediaPlayer::NetworkState networkState() const;
135 virtual WebKit::WebMediaPlayer::ReadyState readyState() const;
137 virtual bool didLoadingProgress() const;
138 virtual unsigned long long totalBytes() const;
140 virtual bool hasSingleSecurityOrigin() const;
141 virtual bool didPassCORSAccessCheck() const;
142 virtual WebKit::WebMediaPlayer::MovieLoadType movieLoadType() const;
144 virtual double mediaTimeForTimeValue(double timeValue) const;
146 virtual unsigned decodedFrameCount() const;
147 virtual unsigned droppedFrameCount() const;
148 virtual unsigned audioDecodedByteCount() const;
149 virtual unsigned videoDecodedByteCount() const;
151 // cc::VideoFrameProvider implementation.
152 virtual void SetVideoFrameProviderClient(
153 cc::VideoFrameProvider::Client* client) OVERRIDE;
154 virtual scoped_refptr<media::VideoFrame> GetCurrentFrame() OVERRIDE;
155 virtual void PutCurrentFrame(const scoped_refptr<media::VideoFrame>& frame)
156 OVERRIDE;
158 virtual bool copyVideoTextureToPlatformTexture(
159 WebKit::WebGraphicsContext3D* web_graphics_context,
160 unsigned int texture,
161 unsigned int level,
162 unsigned int internal_format,
163 unsigned int type,
164 bool premultiply_alpha,
165 bool flip_y);
167 virtual WebKit::WebAudioSourceProvider* audioSourceProvider();
169 virtual MediaKeyException generateKeyRequest(
170 const WebKit::WebString& key_system,
171 const unsigned char* init_data,
172 unsigned init_data_length);
174 virtual MediaKeyException addKey(const WebKit::WebString& key_system,
175 const unsigned char* key,
176 unsigned key_length,
177 const unsigned char* init_data,
178 unsigned init_data_length,
179 const WebKit::WebString& session_id);
181 virtual MediaKeyException cancelKeyRequest(
182 const WebKit::WebString& key_system,
183 const WebKit::WebString& session_id);
185 // As we are closing the tab or even the browser, |main_loop_| is destroyed
186 // even before this object gets destructed, so we need to know when
187 // |main_loop_| is being destroyed and we can stop posting repaint task
188 // to it.
189 virtual void WillDestroyCurrentMessageLoop() OVERRIDE;
191 void Repaint();
193 void OnPipelineSeek(media::PipelineStatus status);
194 void OnPipelineEnded();
195 void OnPipelineError(media::PipelineStatus error);
196 void OnPipelineBufferingState(
197 media::Pipeline::BufferingState buffering_state);
198 void OnDemuxerOpened(scoped_ptr<WebKit::WebMediaSource> media_source);
199 void OnKeyAdded(const std::string& key_system, const std::string& session_id);
200 void OnKeyError(const std::string& key_system,
201 const std::string& session_id,
202 media::Decryptor::KeyError error_code,
203 int system_code);
204 void OnKeyMessage(const std::string& key_system,
205 const std::string& session_id,
206 const std::string& message,
207 const std::string& default_url);
208 void OnNeedKey(const std::string& key_system,
209 const std::string& type,
210 const std::string& session_id,
211 scoped_ptr<uint8[]> init_data,
212 int init_data_size);
213 void SetOpaque(bool);
215 private:
216 // Contains common logic used across the different types loading.
217 void LoadSetup(const WebKit::WebURL& url);
219 // Called after asynchronous initialization of a data source completed.
220 void DataSourceInitialized(const GURL& gurl, bool success);
222 // Called when the data source is downloading or paused.
223 void NotifyDownloading(bool is_downloading);
225 // Finishes starting the pipeline due to a call to load().
227 // A non-null |media_source| will construct a Media Source pipeline.
228 void StartPipeline(WebKit::WebMediaSource* media_source);
230 // Helpers that set the network/ready state and notifies the client if
231 // they've changed.
232 void SetNetworkState(WebKit::WebMediaPlayer::NetworkState state);
233 void SetReadyState(WebKit::WebMediaPlayer::ReadyState state);
235 // Destroy resources held.
236 void Destroy();
238 // Getter method to |client_|.
239 WebKit::WebMediaPlayerClient* GetClient();
241 // Lets V8 know that player uses extra resources not managed by V8.
242 void IncrementExternallyAllocatedMemory();
244 // Actually do the work for generateKeyRequest/addKey so they can easily
245 // report results to UMA.
246 MediaKeyException GenerateKeyRequestInternal(
247 const WebKit::WebString& key_system,
248 const unsigned char* init_data,
249 unsigned init_data_length);
250 MediaKeyException AddKeyInternal(const WebKit::WebString& key_system,
251 const unsigned char* key,
252 unsigned key_length,
253 const unsigned char* init_data,
254 unsigned init_data_length,
255 const WebKit::WebString& session_id);
256 MediaKeyException CancelKeyRequestInternal(
257 const WebKit::WebString& key_system,
258 const WebKit::WebString& session_id);
260 // Gets the duration value reported by the pipeline.
261 double GetPipelineDuration() const;
263 // Notifies WebKit of the duration change.
264 void OnDurationChange();
266 // Called by VideoRendererBase on its internal thread with the new frame to be
267 // painted.
268 void FrameReady(const scoped_refptr<media::VideoFrame>& frame);
270 WebKit::WebFrame* frame_;
272 // TODO(hclam): get rid of these members and read from the pipeline directly.
273 WebKit::WebMediaPlayer::NetworkState network_state_;
274 WebKit::WebMediaPlayer::ReadyState ready_state_;
276 // Keep a list of buffered time ranges.
277 WebKit::WebTimeRanges buffered_;
279 // Message loops for posting tasks on Chrome's main thread. Also used
280 // for DCHECKs so methods calls won't execute in the wrong thread.
281 const scoped_refptr<base::MessageLoopProxy> main_loop_;
283 scoped_ptr<media::Pipeline> pipeline_;
284 base::Thread media_thread_;
286 // The currently selected key system. Empty string means that no key system
287 // has been selected.
288 WebKit::WebString current_key_system_;
290 // Playback state.
292 // TODO(scherkus): we have these because Pipeline favours the simplicity of a
293 // single "playback rate" over worrying about paused/stopped etc... It forces
294 // all clients to manage the pause+playback rate externally, but is that
295 // really a bad thing?
297 // TODO(scherkus): since SetPlaybackRate(0) is asynchronous and we don't want
298 // to hang the render thread during pause(), we record the time at the same
299 // time we pause and then return that value in currentTime(). Otherwise our
300 // clock can creep forward a little bit while the asynchronous
301 // SetPlaybackRate(0) is being executed.
302 bool paused_;
303 bool seeking_;
304 double playback_rate_;
305 base::TimeDelta paused_time_;
307 // Seek gets pending if another seek is in progress. Only last pending seek
308 // will have effect.
309 bool pending_seek_;
310 double pending_seek_seconds_;
312 WebKit::WebMediaPlayerClient* client_;
314 base::WeakPtr<WebMediaPlayerDelegate> delegate_;
316 MediaStreamClient* media_stream_client_;
318 scoped_refptr<media::MediaLog> media_log_;
320 // Since accelerated compositing status is only known after the first layout,
321 // we delay reporting it to UMA until that time.
322 bool accelerated_compositing_reported_;
324 bool incremented_externally_allocated_memory_;
326 // Factories for supporting GpuVideoDecoder. May be null.
327 scoped_refptr<media::GpuVideoDecoder::Factories> gpu_factories_;
329 // Routes audio playback to either AudioRendererSink or WebAudio.
330 scoped_refptr<WebAudioSourceProviderImpl> audio_source_provider_;
332 bool is_local_source_;
333 bool supports_save_;
335 // The decryptor that manages decryption keys and decrypts encrypted frames.
336 scoped_ptr<ProxyDecryptor> decryptor_;
338 bool starting_;
340 // These two are mutually exclusive:
341 // |data_source_| is used for regular resource loads.
342 // |chunk_demuxer_| is used for Media Source resource loads.
344 // |demuxer_| will contain the appropriate demuxer based on which resource
345 // load strategy we're using.
346 scoped_ptr<BufferedDataSource> data_source_;
347 scoped_ptr<media::Demuxer> demuxer_;
348 media::ChunkDemuxer* chunk_demuxer_;
350 // Temporary for EME v0.1. In the future the init data type should be passed
351 // through GenerateKeyRequest() directly from WebKit.
352 std::string init_data_type_;
354 // Video frame rendering members.
356 // |lock_| protects |current_frame_| since new frames arrive on the video
357 // rendering thread, yet are accessed for rendering on either the main thread
358 // or compositing thread depending on whether accelerated compositing is used.
359 base::Lock lock_;
360 media::SkCanvasVideoRenderer skcanvas_video_renderer_;
361 scoped_refptr<media::VideoFrame> current_frame_;
362 bool pending_repaint_;
363 bool pending_size_change_;
365 // The compositor layer for displaying the video content when using composited
366 // playback.
367 scoped_ptr<webkit::WebLayerImpl> video_weblayer_;
369 // A pointer back to the compositor to inform it about state changes. This is
370 // not NULL while the compositor is actively using this webmediaplayer.
371 cc::VideoFrameProvider::Client* video_frame_provider_client_;
373 DISALLOW_COPY_AND_ASSIGN(WebMediaPlayerImpl);
376 } // namespace webkit_media
378 #endif // WEBKIT_MEDIA_WEBMEDIAPLAYER_IMPL_H_