156a7d8071b804702369226747b1961533196ebd
[platform/framework/web/chromium-efl.git] / tizen_src / chromium_impl / media / filters / media_player_esplusplayer.cc
1 // Copyright 2022 Samsung Electronics Inc. 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 "tizen_src/chromium_impl/media/filters/media_player_esplusplayer.h"
6
7 #include <esplusplayer_internal.h>
8 #include <tbm_surface.h>
9
10 #include "base/bind.h"
11 #include "base/callback.h"
12 #include "base/location.h"
13 #include "base/logging.h"
14 #include "media/base/decoder_buffer.h"
15 #include "media/base/renderer_client.h"
16 #include "third_party/libyuv/include/libyuv/convert.h"
17 #include "tizen_src/chromium_impl/media/filters/media_player_registry.h"
18
19 #if defined(TIZEN_VIDEO_HOLE)
20 #include <Ecore_Wl2.h>
21 #include "tizen_src/chromium_impl/media/base/tizen/video_plane_controller_esplusplayer.h"
22 #endif
23
24 namespace media {
25 using player_buffer_size_t = unsigned long long;
26
27 // Limit of platform player's total (audio and video) buffer size in bytes
28 const media::player_buffer_size_t kPlayerTotalBufferSize = 64 * 1024 * 1024;
29 // Limit of platform player's audio buffer in bytes
30 const media::player_buffer_size_t kPlayerAudioBufferSize = 768 * 1024;
31
32 espp_buffer_size_t GetMaxAudioBufferSize() {
33   return kPlayerAudioBufferSize;
34 }
35
36 espp_buffer_size_t GetMaxVideoBufferSize(gfx::Size size) {
37   return kPlayerTotalBufferSize - kPlayerAudioBufferSize;
38 }
39
40 void ReadyToPrepareCallback(const esplusplayer_stream_type stream_type,
41                             void* user_data) {
42   MediaPlayerESPlusPlayer* player =
43       static_cast<MediaPlayerESPlusPlayer*>(user_data);
44   if (!player)
45     return;
46
47   player->OnReadyToPrepare(stream_type);
48 }
49
50 void PrepareCompleteCallback(bool result, void* user_data) {
51   MediaPlayerESPlusPlayer* player =
52       static_cast<MediaPlayerESPlusPlayer*>(user_data);
53   if (!player)
54     return;
55
56   player->OnPrepareComplete(result);
57 }
58
59 void EosCallback(void* user_data) {
60   MediaPlayerESPlusPlayer* player =
61       static_cast<MediaPlayerESPlusPlayer*>(user_data);
62   if (!player)
63     return;
64
65   player->OnEos();
66 }
67
68 void FrameReadyCallback(const esplusplayer_decoded_video_packet* packet,
69                         void* user_data) {
70   MediaPlayerESPlusPlayer* player =
71       static_cast<MediaPlayerESPlusPlayer*>(user_data);
72   if (!player)
73     return;
74
75   player->OnFrameReady(packet);
76 }
77
78 void FlushCompleteCallback(void* user_data) {
79   MediaPlayerESPlusPlayer* player =
80       static_cast<MediaPlayerESPlusPlayer*>(user_data);
81   if (!player)
82     return;
83
84   player->OnFlushComplete();
85 }
86
87 void ReadyToSeekCallback(const esplusplayer_stream_type stream_type,
88                          const uint64_t seek_time,
89                          void* user_data) {
90   MediaPlayerESPlusPlayer* player =
91       static_cast<MediaPlayerESPlusPlayer*>(user_data);
92   if (!player)
93     return;
94
95   player->OnReadyToSeek(stream_type, seek_time);
96 }
97
98 void SeekCompleteCallback(void* user_data) {
99   MediaPlayerESPlusPlayer* player =
100       static_cast<MediaPlayerESPlusPlayer*>(user_data);
101   if (!player)
102     return;
103
104   player->OnSeekComplete();
105 }
106
107 void ResourceConflictCallback(void* user_data) {
108   MediaPlayerESPlusPlayer* player =
109       static_cast<MediaPlayerESPlusPlayer*>(user_data);
110   if (!player)
111     return;
112
113   player->OnResourceConflict();
114 }
115
116 void ErrorCallback(const esplusplayer_error_type error_type, void* user_data) {
117   MediaPlayerESPlusPlayer* player =
118       static_cast<MediaPlayerESPlusPlayer*>(user_data);
119   if (!player)
120     return;
121
122   player->OnError(error_type);
123 }
124
125 MediaPlayerESPlusPlayer::MediaPlayerESPlusPlayer() {
126   LOG(INFO) << "(" << static_cast<void*>(this) << ") " << __func__;
127   player_id_ = MediaPlayerRegistry::GetInstance()->RegisterMediaPlayer(this);
128 }
129
130 MediaPlayerESPlusPlayer::~MediaPlayerESPlusPlayer() {
131   LOG(INFO) << "(" << static_cast<void*>(this) << ") " << __func__;
132   weak_factory_.InvalidateWeakPtrs();
133
134   MediaPlayerRegistry::GetInstance()->UnregisterMediaPlayer(player_id_);
135
136   // Player should be released before destroyed.
137   Release();
138
139   int error = esplusplayer_destroy(esplayer_);
140   if (error != ESPLUSPLAYER_ERROR_TYPE_NONE)
141     LOG(ERROR) << "esplusplayer_destroy failed, error #"
142                << esplusplayer_get_error_string(
143                       static_cast<esplusplayer_error_type>(error));
144   esplayer_ = nullptr;
145 }
146
147 bool MediaPlayerESPlusPlayer::CreatePlayer() {
148   if (esplayer_)
149     return true;
150
151   LOG(INFO) << "(" << static_cast<void*>(this) << ") " << __func__;
152   esplayer_ = esplusplayer_create();
153   if (!esplayer_) {
154     LOG(ERROR) << "Cannot create esplus player!";
155     return false;
156   }
157
158   last_frames_.get<DemuxerStream::AUDIO>().first = media::kNoTimestamp;
159   last_frames_.get<DemuxerStream::AUDIO>().second = media::kNoTimestamp;
160   last_frames_.get<DemuxerStream::VIDEO>().first = media::kNoTimestamp;
161   last_frames_.get<DemuxerStream::VIDEO>().second = media::kNoTimestamp;
162
163   buffer_observer_.reset(BufferObserver::CreateBufferObserver());
164
165 #if defined(TIZEN_VIDEO_HOLE)
166   LOG(INFO) << __func__ << " is_video_hole_: " << is_video_hole_;
167   if (is_video_hole_) {
168     video_plane_controller_.reset(
169         new VideoPlaneControllerESPlusPlayer(esplayer_));
170   }
171 #endif
172
173   return true;
174 }
175
176 void MediaPlayerESPlusPlayer::Initialize(VideoRendererSink* sink) {
177   LOG(INFO) << "(" << static_cast<void*>(this) << ") " << __func__;
178   esplusplayer_set_ready_to_prepare_cb(esplayer_, &ReadyToPrepareCallback,
179                                        this);
180   esplusplayer_set_prepare_async_done_cb(esplayer_, &PrepareCompleteCallback,
181                                          this);
182   esplusplayer_set_eos_cb(esplayer_, &EosCallback, this);
183   esplusplayer_set_media_packet_video_decoded_cb(esplayer_, &FrameReadyCallback,
184                                                  this);
185   esplusplayer_set_flush_done_cb(esplayer_, &FlushCompleteCallback, this);
186   esplusplayer_set_ready_to_seek_cb(esplayer_, &ReadyToSeekCallback, this);
187   esplusplayer_set_seek_done_cb(esplayer_, &SeekCompleteCallback, this);
188   esplusplayer_set_resource_conflicted_cb(esplayer_, &ResourceConflictCallback,
189                                           this);
190   esplusplayer_set_error_cb(esplayer_, &ErrorCallback, this);
191   buffer_observer_->SetBufferingCallback(
192       base::BindRepeating(&MediaPlayerESPlusPlayer::OnBufferingStatusChanged,
193                           weak_factory_.GetWeakPtr()));
194
195   int error = esplusplayer_open(esplayer_);
196   if (error != ESPLUSPLAYER_ERROR_TYPE_NONE) {
197     LOG(ERROR) << "esplusplayer_open failed. error #"
198                << esplusplayer_get_error_string(
199                       static_cast<esplusplayer_error_type>(error));
200     return;
201   }
202
203   LOG(INFO) << "(" << static_cast<void*>(this) << ") " << __func__
204             << " state:" << GetString(GetPlayerState());
205
206   esplusplayer_decoded_video_frame_buffer_type video_frame_buffer_type =
207       ESPLUSPLAYER_DECODED_VIDEO_FRAME_BUFFER_TYPE_COPY;
208 #if defined(TIZEN_VIDEO_HOLE)
209   if (is_video_hole_)
210     video_frame_buffer_type = ESPLUSPLAYER_DECODED_VIDEO_FRAME_BUFFER_TYPE_NONE;
211 #endif
212
213   error = esplusplayer_set_video_frame_buffer_type(esplayer_,
214                                                    video_frame_buffer_type);
215   if (error != ESPLUSPLAYER_ERROR_TYPE_NONE) {
216     LOG(ERROR) << "esplusplayer_set_video_frame_buffer_type failed. error #"
217                << esplusplayer_get_error_string(
218                       static_cast<esplusplayer_error_type>(error));
219     return;
220   }
221
222   sink_ = sink;
223 }
224
225 bool MediaPlayerESPlusPlayer::IsInitialized() {
226   return (GetPlayerState() >= ESPLUSPLAYER_STATE_IDLE);
227 }
228
229 void MediaPlayerESPlusPlayer::SetTaskRunner(
230     const scoped_refptr<base::SingleThreadTaskRunner>& task_runner) {
231   task_runner_ = task_runner.get();
232 }
233
234 void MediaPlayerESPlusPlayer::SetStreamInfo(DemuxerStream::Type type,
235                                             DemuxerStream* stream,
236                                             RendererClient* client) {
237   if (!esplayer_) {
238     LOG(ERROR) << "Invalid player handle. Send error to client.";
239     client->OnError(PIPELINE_ERROR_INITIALIZATION_FAILED);
240     return;
241   }
242
243   SetDemuxerStream(type, stream);
244   SetRendererClient(type, client);
245   InitializeStreamConfig(type);
246 }
247
248 void MediaPlayerESPlusPlayer::SetRendererClientExtension(
249     media::MediaPlayerTizenClientExtension* client_extension) {
250   NOTIMPLEMENTED();
251 }
252
253 void MediaPlayerESPlusPlayer::Prepare() {
254   LOG(INFO) << "(" << static_cast<void*>(this) << ") " << __func__;
255   if (is_prepared_ || is_preparing_)
256     return;
257
258   if (GetPlayerState() != ESPLUSPLAYER_STATE_IDLE) {
259     LOG(ERROR) << "(" << static_cast<void*>(this) << ") " << __func__
260                << " Prepare called on invalid state : "
261                << GetString(GetPlayerState());
262     return;
263   }
264
265 #if defined(TIZEN_VIDEO_HOLE)
266   if (is_video_hole_ && video_plane_controller_) {
267     if (video_plane_controller_->Initialize() != TIZEN_ERROR_NONE) {
268       LOG(ERROR) << "video_plane_controller init error";
269       return;
270     }
271     LOG(INFO) << __func__ << " set ESPLUSPLAYER_DISPLAY_TYPE_OVERLAY";
272     int player_error = ESPLUSPLAYER_ERROR_TYPE_NONE;
273     if (video_plane_controller_->rendering_mode() ==
274         VideoPlaneController::RenderingMode::OFFSCREEN) {
275       player_error = esplusplayer_set_display(
276           esplayer_, ESPLUSPLAYER_DISPLAY_TYPE_OVERLAY,
277           video_plane_controller_->GetVideoPlaneHandle());
278     } else {
279       int wl_w, wl_h, wl_x, wl_y;
280       ecore_wl2_window_geometry_get(
281           static_cast<Ecore_Wl2_Window*>(
282               video_plane_controller_->GetVideoPlaneHandle()),
283           &wl_x, &wl_y, &wl_w, &wl_h);
284
285       player_error = esplusplayer_set_ecore_display(
286           esplayer_, ESPLUSPLAYER_DISPLAY_TYPE_OVERLAY,
287           static_cast<Ecore_Wl2_Window*>(
288               video_plane_controller_->GetVideoPlaneHandle()),
289           wl_x, wl_y, wl_w, wl_h);
290     }
291     if (player_error != ESPLUSPLAYER_ERROR_TYPE_NONE) {
292       LOG(ERROR) << "player_error #"
293                  << esplusplayer_get_error_string(
294                         static_cast<esplusplayer_error_type>(player_error));
295       return;
296     }
297   }
298 #endif
299
300   int error = esplusplayer_prepare_async(esplayer_);
301   if (error != ESPLUSPLAYER_ERROR_TYPE_NONE) {
302     LOG(ERROR) << "player prepare failed! error #"
303                << esplusplayer_get_error_string(
304                       static_cast<esplusplayer_error_type>(error));
305
306     if (IsValid(DemuxerStream::AUDIO))
307       GetRendererClient(DemuxerStream::AUDIO)
308           ->OnError(PIPELINE_ERROR_INITIALIZATION_FAILED);
309     else if (IsValid(DemuxerStream::VIDEO))
310       GetRendererClient(DemuxerStream::VIDEO)
311           ->OnError(PIPELINE_ERROR_INITIALIZATION_FAILED);
312     return;
313   }
314   is_preparing_ = true;
315 }
316
317 bool MediaPlayerESPlusPlayer::IsPrepared() {
318   return (GetPlayerState() >= ESPLUSPLAYER_STATE_READY);
319 }
320
321 void MediaPlayerESPlusPlayer::Release() {
322   if (!esplayer_)
323     return;
324
325   LOG(INFO) << "(" << static_cast<void*>(this) << ") " << __func__;
326   SetIsEos(DemuxerStream::AUDIO, false);
327   SetShouldFeed(DemuxerStream::AUDIO, false);
328   SetIsValid(DemuxerStream::AUDIO, false);
329   SetReadRequested(DemuxerStream::AUDIO, false);
330
331   SetIsEos(DemuxerStream::VIDEO, false);
332   SetShouldFeed(DemuxerStream::VIDEO, false);
333   SetIsValid(DemuxerStream::VIDEO, false);
334   SetReadRequested(DemuxerStream::VIDEO, false);
335
336   esplusplayer_set_ready_to_prepare_cb(esplayer_, nullptr, this);
337   esplusplayer_set_prepare_async_done_cb(esplayer_, nullptr, this);
338   esplusplayer_set_eos_cb(esplayer_, nullptr, this);
339   esplusplayer_set_media_packet_video_decoded_cb(esplayer_, nullptr, this);
340   esplusplayer_set_flush_done_cb(esplayer_, nullptr, this);
341   esplusplayer_set_ready_to_seek_cb(esplayer_, nullptr, this);
342   esplusplayer_set_seek_done_cb(esplayer_, nullptr, this);
343   esplusplayer_set_resource_conflicted_cb(esplayer_, nullptr, this);
344   esplusplayer_set_error_cb(esplayer_, nullptr, this);
345
346   buffer_observer_->ResetBufferStatus();
347   buffer_observer_->ResetBufferStatusCallbacks(esplayer_);
348
349   volume_ = 1.0;
350   playback_rate_ = 0.0;
351   is_prepared_ = false;
352   is_preparing_ = false;
353   is_paused_ = true;
354   is_buffering_ = false;
355   current_position_ = base::TimeDelta();
356   is_flushing_ = false;
357   is_seeking_ = false;
358   seek_position_ = base::TimeDelta();
359   pending_seek_ = false;
360   pending_seek_position_ = base::TimeDelta();
361   should_set_playback_rate_ = false;
362
363   GetBufferQueue(DemuxerStream::VIDEO).clear();
364   GetBufferQueue(DemuxerStream::AUDIO).clear();
365   data_cb_.Reset();
366   sink_ = nullptr;
367
368   if (GetPlayerState() == ESPLUSPLAYER_STATE_NONE) {
369     LOG(ERROR) << "(" << static_cast<void*>(this) << ") " << __func__
370                << " Release called on invalid state : "
371                << GetString(GetPlayerState());
372     return;
373   }
374
375   esplusplayer_close(esplayer_);
376 }
377
378 void MediaPlayerESPlusPlayer::Play() {
379   LOG(INFO) << "(" << static_cast<void*>(this) << ") " << __func__;
380   int error = ESPLUSPLAYER_ERROR_TYPE_NONE;
381   esplusplayer_state state = GetPlayerState();
382
383   is_paused_ = false;
384   if (state < ESPLUSPLAYER_STATE_READY || !is_prepared_ || is_seeking_) {
385     LOG(INFO) << "state : " << GetString(state)
386               << " is_prepared : " << is_prepared_
387               << " is_seeking : " << is_seeking_
388               << " is_buffering : " << is_buffering_;
389     return;
390   }
391
392   if (is_buffering_) {
393     LOG(INFO) << "state : " << GetString(state) << " is_paused : " << is_paused_
394               << " is_buffering : " << is_buffering_;
395     // return;
396   }
397
398   SetVolume(volume_);
399   if (should_set_playback_rate_)
400     SetRate(playback_rate_);
401
402   if (state == ESPLUSPLAYER_STATE_READY)
403     error = esplusplayer_start(esplayer_);
404   else if (state == ESPLUSPLAYER_STATE_PAUSED ||
405            state == ESPLUSPLAYER_STATE_PLAYING)
406     error = esplusplayer_resume(esplayer_);
407
408   if (error != ESPLUSPLAYER_ERROR_TYPE_NONE) {
409     LOG(ERROR) << "player play failed! state #" << GetString(state)
410                << " error #"
411                << esplusplayer_get_error_string(
412                       static_cast<esplusplayer_error_type>(error));
413     // TODO: handle error!
414     return;
415   }
416 }
417
418 void MediaPlayerESPlusPlayer::Pause(bool is_media_related_action) {
419   if (is_paused_) {
420     LOG(INFO) << "(" << static_cast<void*>(this) << ") " << __func__
421               << " already paused";
422     return;
423   }
424
425   if (!is_media_related_action)
426     is_paused_ = true;
427
428   LOG(INFO) << "(" << static_cast<void*>(this) << ") " << __func__
429             << " is_buffering : " << is_buffering_
430             << " is_media_action : " << is_media_related_action;
431   esplusplayer_state state = GetPlayerState();
432   if (state != ESPLUSPLAYER_STATE_PLAYING) {
433     LOG(WARNING) << "Cannot pause in " << GetString(state) << " state";
434     return;
435   }
436
437   int error = esplusplayer_pause(esplayer_);
438   if (error != ESPLUSPLAYER_ERROR_TYPE_NONE) {
439     LOG(ERROR) << "player pause failed! error #"
440                << esplusplayer_get_error_string(
441                       static_cast<esplusplayer_error_type>(error));
442     // TODO: handle error!
443     return;
444   }
445 }
446
447 void MediaPlayerESPlusPlayer::SetRate(double rate) {
448   LOG(INFO) << "(" << static_cast<void*>(this) << ") " << __func__ << " : "
449             << rate;
450   if (playback_rate_ == rate)
451     return;
452
453   playback_rate_ = rate;
454   if (GetPlayerState() < ESPLUSPLAYER_STATE_READY) {
455     should_set_playback_rate_ = true;
456     return;
457   }
458
459   bool should_mute = rate >= 2.0;
460   int error =
461       esplusplayer_set_playback_rate(esplayer_, playback_rate_, should_mute);
462   if (error != ESPLUSPLAYER_ERROR_TYPE_NONE) {
463     LOG(ERROR) << "player set playback rate failed! error #"
464                << esplusplayer_get_error_string(
465                       static_cast<esplusplayer_error_type>(error));
466     return;
467   }
468   should_set_playback_rate_ = false;
469 }
470
471 void MediaPlayerESPlusPlayer::Seek(base::TimeDelta time) {
472   // Ignore seek to 0 during initialization.
473   if (GetPlayerState() < ESPLUSPLAYER_STATE_READY && time.InSecondsF() == 00) {
474     LOG(INFO) << __func__ << " Ignore seek to 0 during initialization.";
475     return;
476   }
477
478   LOG(INFO) << "(" << static_cast<void*>(this) << ") " << __func__ << " :"
479             << time;
480   if (GetPlayerState() < ESPLUSPLAYER_STATE_READY || !is_prepared_ ||
481       is_seeking_) {
482     LOG(INFO) << "Add to pending seek ("
483               << ") state: " << GetString(GetPlayerState())
484               << " is_prepared : " << is_prepared_
485               << " is_seeking : " << is_seeking_;
486     pending_seek_ = true;
487     pending_seek_position_ = time;
488     return;
489   }
490
491   last_frames_.get<DemuxerStream::AUDIO>().first = media::kNoTimestamp;
492   last_frames_.get<DemuxerStream::VIDEO>().first = media::kNoTimestamp;
493
494   UpdateBufferedDtsDifference();
495
496   SetShouldFeed(DemuxerStream::AUDIO, false);
497   SetShouldFeed(DemuxerStream::VIDEO, false);
498   GetBufferQueue(DemuxerStream::VIDEO).clear();
499   GetBufferQueue(DemuxerStream::AUDIO).clear();
500   buffer_observer_->ResetBufferStatus();
501
502   LOG(INFO) << __func__ << " : " << time;
503   int error = esplusplayer_seek(esplayer_, time.InMilliseconds());
504   if (error != ESPLUSPLAYER_ERROR_TYPE_NONE) {
505     LOG(ERROR) << "Seek failed. Current time : " << time.InSecondsF()
506                << " error #"
507                << esplusplayer_get_error_string(
508                       static_cast<esplusplayer_error_type>(error));
509     return;
510   }
511
512   is_seeking_ = true;
513   seek_position_ = time;
514   pending_seek_ = false;
515   pending_seek_position_ = base::TimeDelta();
516 }
517
518 void MediaPlayerESPlusPlayer::Flush(base::OnceClosure flush_cb) {
519   LOG(INFO) << "(" << static_cast<void*>(this) << ") " << __func__;
520   last_frames_.get<DemuxerStream::AUDIO>().first = media::kNoTimestamp;
521   last_frames_.get<DemuxerStream::VIDEO>().first = media::kNoTimestamp;
522
523   UpdateBufferedDtsDifference();
524
525   NOTIMPLEMENTED();
526   std::move(flush_cb).Run();
527 }
528
529 void MediaPlayerESPlusPlayer::SetVolume(double volume) {
530   LOG(INFO) << "(" << static_cast<void*>(this) << ") " << __func__ << " :"
531             << volume;
532   volume_ = volume;
533   if (GetPlayerState() == ESPLUSPLAYER_STATE_NONE)
534     return;
535
536   int error = esplusplayer_set_volume(esplayer_, 100 * volume_);
537   if (error != ESPLUSPLAYER_ERROR_TYPE_NONE)
538     LOG(ERROR) << "esplusplayer_set_volume failed, error #"
539                << esplusplayer_get_error_string(
540                       static_cast<esplusplayer_error_type>(error));
541 }
542
543 base::TimeDelta MediaPlayerESPlusPlayer::GetCurrentTime() {
544   if (pending_seek_)
545     return pending_seek_position_;
546
547   if (is_seeking_)
548     return seek_position_;
549
550   // Seek can be called before PLAY / PAUSE. Return last known time.
551   if (GetPlayerState() < ESPLUSPLAYER_STATE_PLAYING)
552     return current_position_;
553
554   uint64_t time = 0;  // In milliseconds.
555   int error = esplusplayer_get_playing_time(esplayer_, &time);
556   if (error != ESPLUSPLAYER_ERROR_TYPE_NONE) {
557     LOG(ERROR) << "esplusplayer_get_playing_time failed. error #"
558                << esplusplayer_get_error_string(
559                       static_cast<esplusplayer_error_type>(error));
560     return base::TimeDelta();
561   }
562
563   current_position_ = base::Milliseconds(time);
564   return current_position_;
565 }
566
567 #if defined(TIZEN_TBM_SUPPORT)
568 void MediaPlayerESPlusPlayer::DestroyMediaPacket(void* media_packet) {
569   if (!task_runner_->BelongsToCurrentThread()) {
570     task_runner_->PostTask(
571         FROM_HERE, base::BindOnce(&MediaPlayerESPlusPlayer::DestroyMediaPacket,
572                                   weak_factory_.GetWeakPtr(), media_packet));
573     return;
574   }
575
576   esplusplayer_decoded_buffer_destroy(
577       esplayer_, static_cast<esplusplayer_decoded_video_packet*>(media_packet));
578 }
579 #endif
580
581 esplusplayer_state MediaPlayerESPlusPlayer::GetPlayerState() {
582   return (esplayer_ ? esplusplayer_get_state(esplayer_)
583                     : ESPLUSPLAYER_STATE_NONE);
584 }
585
586 void MediaPlayerESPlusPlayer::InitializeStreamConfig(DemuxerStream::Type type) {
587   LOG(INFO) << "(" << static_cast<void*>(this) << ") " << __func__;
588   DemuxerStream* stream = GetDemuxerStream(type);
589   CHECK(stream);
590
591   if (type == DemuxerStream::AUDIO) {
592     media::AudioDecoderConfig audio_config = stream->audio_decoder_config();
593     if (!audio_config.IsValidConfig()) {
594       LOG(INFO) << "Invalid audio config";
595       return;
596     }
597
598     LOG(INFO) << "Audio config : " << audio_config.AsHumanReadableString();
599     esplusplayer_audio_stream_info audio_stream_info;
600     memset(&audio_stream_info, 0, sizeof(esplusplayer_audio_stream_info));
601
602     audio_stream_info.mime_type =
603         ConvertToESPlusAudioMimeType(audio_config.codec());
604     audio_stream_info.bitrate = audio_config.bytes_per_channel() *
605                                 audio_config.samples_per_second() * 8;
606     audio_stream_info.channels =
607         media::ChannelLayoutToChannelCount(audio_config.channel_layout());
608     audio_stream_info.sample_rate = audio_config.samples_per_second();
609     audio_stream_info.codec_data_length = audio_config.extra_data().size();
610
611     if (audio_stream_info.codec_data_length > 0) {
612       audio_stream_info.codec_data =
613           (char*)(const_cast<unsigned char*>(audio_config.extra_data().data()));
614     } else {
615       audio_stream_info.codec_data = NULL;
616     }
617
618     int error;
619     if (!IsValid(type)) {
620       error = esplusplayer_set_audio_stream_info(esplayer_, &audio_stream_info);
621       if (error != ESPLUSPLAYER_ERROR_TYPE_NONE) {
622         LOG(ERROR) << "esplusplayer_set_audio_stream_info failed. error code "
623                    << error;
624         GetRendererClient(type)->OnError(PIPELINE_ERROR_INITIALIZATION_FAILED);
625         return;
626       }
627       buffer_observer_->SetMediaStreamStatusCallback(
628           esplayer_, ESPLUSPLAYER_STREAM_TYPE_AUDIO);
629     }
630
631     espp_buffer_size_t max_buffer_size = GetMaxAudioBufferSize();
632     buffer_observer_->SetBufferSize(type, max_buffer_size);
633     LOG(INFO) << "Audio Max buffer size " << max_buffer_size;
634     error = esplusplayer_set_buffer_size(
635         esplayer_, ESPLUSPLAYER_BUFFER_AUDIO_MAX_BYTE_SIZE, max_buffer_size);
636     if (error != ESPLUSPLAYER_ERROR_TYPE_NONE)
637       LOG(WARNING) << "Failed to set audio buffer to " << max_buffer_size / 1024
638                    << "KB";
639
640     SetIsValid(type, true);
641     GetRendererClient(type)->OnAudioConfigChange(audio_config);
642   }
643
644   if (type == DemuxerStream::VIDEO) {
645     media::VideoDecoderConfig video_config = stream->video_decoder_config();
646     if (!video_config.IsValidConfig()) {
647       LOG(ERROR) << "Invalid video config.";
648       return;
649     }
650
651     LOG(INFO) << "Video config : " << video_config.AsHumanReadableString();
652     esplusplayer_video_stream_info video_stream_info;
653     memset(&video_stream_info, 0, sizeof(esplusplayer_video_stream_info));
654
655     video_stream_info.width = video_config.coded_size().width();
656     video_stream_info.height = video_config.coded_size().height();
657     video_stream_info.mime_type =
658         ConvertToESPlusVideoMimeType(video_config.codec());
659
660     // TODO: Fetch frame rate from demuxer?
661     video_stream_info.framerate_num = kVideoFramerateNum;
662     video_stream_info.framerate_den = kVideoFramerateDen;
663     video_stream_info.codec_data_length = video_config.extra_data().size();
664     if (video_stream_info.codec_data_length > 0) {
665       video_stream_info.codec_data =
666           (char*)(const_cast<unsigned char*>(video_config.extra_data().data()));
667     } else {
668       video_stream_info.codec_data = NULL;
669     }
670     auto max_resolution =
671         GetMaxCodecResolution(video_stream_info.mime_type, is_video_hole_);
672
673     video_stream_info.max_width = max_resolution.width();
674     video_stream_info.max_height = max_resolution.height();
675
676     int error;
677     if (!IsValid(type)) {
678       error = esplusplayer_set_video_stream_info(esplayer_, &video_stream_info);
679       if (error != ESPLUSPLAYER_ERROR_TYPE_NONE) {
680         LOG(ERROR) << "esplusplayer_set_video_stream_info failed. error code "
681                    << error;
682         GetRendererClient(type)->OnError(PIPELINE_ERROR_INITIALIZATION_FAILED);
683         return;
684       }
685       buffer_observer_->SetMediaStreamStatusCallback(
686           esplayer_, ESPLUSPLAYER_STREAM_TYPE_VIDEO);
687     }
688
689     espp_buffer_size_t max_buffer_size =
690         GetMaxVideoBufferSize(video_config.coded_size());
691     buffer_observer_->SetBufferSize(type, max_buffer_size);
692
693     LOG(INFO) << "Video Max buffer size " << max_buffer_size;
694     error = esplusplayer_set_buffer_size(
695         esplayer_, ESPLUSPLAYER_BUFFER_VIDEO_MAX_BYTE_SIZE, max_buffer_size);
696     if (error != ESPLUSPLAYER_ERROR_TYPE_NONE)
697       LOG(WARNING) << "Failed to set video buffer to " << max_buffer_size / 1024
698                    << "KB";
699
700     SetIsValid(type, true);
701     GetRendererClient(type)->OnVideoConfigChange(video_config);
702   }
703 }
704
705 void MediaPlayerESPlusPlayer::ReadBuffer(DemuxerStream::Type type) {
706   if (!ReadFromBufferQueue(type))
707     return;
708
709   // Avoid unnecessary or redundant read requests.
710   if (!ShouldFeed(type) || ReadRequested(type) || IsEos(type))
711     return;
712
713   SetReadRequested(type, true);
714   GetDemuxerStream(type)->Read(
715       base::BindOnce(&MediaPlayerESPlusPlayer::OnBufferReady,
716                      weak_factory_.GetWeakPtr(), type));
717 }
718
719 void MediaPlayerESPlusPlayer::OnBufferReady(
720     DemuxerStream::Type type,
721     DemuxerStream::Status status,
722     scoped_refptr<DecoderBuffer> buffer) {
723   switch (status) {
724     case DemuxerStream::kAborted:
725     case DemuxerStream::kError:
726       GetBufferQueue(type).clear();
727       break;
728     case DemuxerStream::kNeedBuffer:
729       break;
730     case DemuxerStream::kConfigChanged:
731       // Clear pending buffer of older config
732       GetBufferQueue(type).clear();
733       InitializeStreamConfig(type);
734       break;
735     case DemuxerStream::kOk: {
736       GetBufferQueue(type).push_back(buffer);
737       break;
738     }
739   }
740
741   SetReadRequested(type, false);
742   ReadBuffer(type);
743 }
744
745 bool MediaPlayerESPlusPlayer::ReadFromBufferQueue(DemuxerStream::Type type) {
746   if (!GetBufferQueue(type).size())
747     return true;
748
749   esplusplayer_submit_status status = ESPLUSPLAYER_SUBMIT_STATUS_SUCCESS;
750   scoped_refptr<DecoderBuffer> buffer = GetBufferQueue(type).front();
751   if (buffer.get()->end_of_stream())
752     status = SubmitEosPacket(type);
753   else
754     status = SubmitEsPacket(type, buffer);
755
756   if (status == ESPLUSPLAYER_SUBMIT_STATUS_NOT_PREPARED ||
757       status == ESPLUSPLAYER_SUBMIT_STATUS_OUT_OF_MEMORY ||
758       status == ESPLUSPLAYER_SUBMIT_STATUS_FULL) {
759     return false;
760   }
761
762   UpdateBufferedDtsDifference();
763   GetBufferQueue(type).pop_front();
764   return true;
765 }
766
767 esplusplayer_submit_status MediaPlayerESPlusPlayer::SubmitEosPacket(
768     DemuxerStream::Type type) {
769   if (IsEos(type))
770     return ESPLUSPLAYER_SUBMIT_STATUS_SUCCESS;
771
772   last_frames_[type].first = base::TimeDelta::Max();
773
774   esplusplayer_submit_status status = esplusplayer_submit_eos_packet(
775       esplayer_, GetESPlusPlayerStreamType(type));
776   if (status != ESPLUSPLAYER_SUBMIT_STATUS_SUCCESS) {
777     LOG(ERROR) << "Submit Eos (" << DemuxerStream::GetTypeName(type)
778                << ") Packet failed, ret:" << GetString(status);
779     return status;
780   }
781   buffer_observer_->SetEos(type);
782   SetIsEos(type, true);
783   return status;
784 }
785
786 esplusplayer_submit_status MediaPlayerESPlusPlayer::SubmitEsPacket(
787     DemuxerStream::Type type,
788     scoped_refptr<DecoderBuffer> buffer) {
789   esplusplayer_es_packet packet;
790   memset(&packet, 0, sizeof(esplusplayer_es_packet));
791   packet.type = GetESPlusPlayerStreamType(type);
792
793   packet.buffer = (char*)(const_cast<unsigned char*>(buffer->data()));
794   packet.buffer_size = buffer->data_size();
795   packet.pts = buffer->timestamp().InMilliseconds();
796   packet.duration = buffer->duration().InMilliseconds();
797
798   // This filed only set when PushMediaPacket
799   packet.matroska_color_info = nullptr;
800   esplusplayer_submit_status status =
801       esplusplayer_submit_packet(esplayer_, &packet);
802   if (status != ESPLUSPLAYER_SUBMIT_STATUS_SUCCESS) {
803     LOG(WARNING) << "submit " << DemuxerStream::GetTypeName(type)
804                  << " packet : " << GetString(status);
805   }
806
807   last_frames_[type].first = base::Milliseconds(packet.pts);
808   last_frames_[type].second = base::Milliseconds(packet.duration);
809   return status;
810 }
811
812 void MediaPlayerESPlusPlayer::UpdateBufferedDtsDifference() {
813   // Ignore unless audio and video streams are valid.
814   if (!IsValid(DemuxerStream::AUDIO) || !IsValid(DemuxerStream::VIDEO))
815     return;
816
817   const auto& audio_ts = last_frames_.get<DemuxerStream::AUDIO>().first;
818   const auto& video_ts = last_frames_.get<DemuxerStream::VIDEO>().first;
819
820   if ((audio_ts != media::kNoTimestamp) && (video_ts != media::kNoTimestamp) &&
821       (audio_ts != base::TimeDelta::Max()) &&
822       (video_ts != base::TimeDelta::Max())) {
823     const auto av_diff = (audio_ts - video_ts).InMilliseconds();
824     buffer_observer_->SetAudioVideoDtsDifference(av_diff);
825   } else {
826     buffer_observer_->SetAudioVideoDtsDifference(0);
827   }
828 }
829
830 void MediaPlayerESPlusPlayer::OnBufferingStatusChanged(DemuxerStream::Type type,
831                                                        BufferStatus status) {
832   LOG(INFO) << __func__ << " " << DemuxerStream::GetTypeName(type) << " : "
833             << GetString(status);
834   const auto RequestStateChange = [this](esplusplayer_state state) {
835     LOG(INFO) << __func__ << " req. change state : " << GetString(state);
836     switch (state) {
837       case ESPLUSPLAYER_STATE_PLAYING:
838         Play();
839         break;
840       case ESPLUSPLAYER_STATE_PAUSED:
841         Pause(true);
842         break;
843       default:
844         NOTREACHED();
845     }
846   };
847
848   SetBufferStatus(type, status);
849   switch (status) {
850     case kBufferUnderrun:
851       //  RequestStateChange(ESPLUSPLAYER_STATE_PAUSED);
852       [[fallthrough]];
853     case kBufferMinThreshold:
854     case kBufferNormal:
855       is_buffering_ = true;
856       SetShouldFeed(type, true);
857       ReadBuffer(type);
858       break;
859     case kBufferMaxThreshold:
860     case kBufferOverflow:
861     case kBufferEos:
862     case kBufferAhead:
863       is_buffering_ = false;
864       SetShouldFeed(type, false);
865       //  if (!is_paused_)
866       //    RequestStateChange(ESPLUSPLAYER_STATE_PLAYING);
867       break;
868     case kBufferNone:
869       NOTREACHED();
870   }
871
872   // TODO: Check if controller can control underflow. Currently buffering
873   // related state changes are commented for the same (in Play and
874   // RequestStateChange).
875   if (status != kBufferNone) {
876     GetRendererClient(type)->OnBufferingStateChange(
877         BUFFERING_HAVE_ENOUGH, BUFFERING_CHANGE_REASON_UNKNOWN);
878   }
879 }
880
881 void MediaPlayerESPlusPlayer::OnReadyToPrepare(
882     const esplusplayer_stream_type stream_type) {
883   if (!task_runner_->BelongsToCurrentThread()) {
884     task_runner_->PostTask(
885         FROM_HERE, base::BindOnce(&MediaPlayerESPlusPlayer::OnReadyToPrepare,
886                                   weak_factory_.GetWeakPtr(), stream_type));
887     return;
888   }
889
890   LOG(INFO) << "OnReadyToPrepare : "
891             << DemuxerStream::GetTypeName(GetDemuxerStreamType(stream_type));
892   if (stream_type != ESPLUSPLAYER_STREAM_TYPE_AUDIO &&
893       stream_type != ESPLUSPLAYER_STREAM_TYPE_VIDEO)
894     return;
895
896   DemuxerStream::Type type = GetDemuxerStreamType(stream_type);
897   if (IsValid(type)) {
898     SetShouldFeed(type, true);
899     ReadBuffer(type);
900   }
901 }
902
903 void MediaPlayerESPlusPlayer::OnPrepareComplete(bool result) {
904   if (!task_runner_->BelongsToCurrentThread()) {
905     task_runner_->PostTask(
906         FROM_HERE, base::BindOnce(&MediaPlayerESPlusPlayer::OnPrepareComplete,
907                                   weak_factory_.GetWeakPtr(), result));
908     return;
909   }
910
911   if (!result) {
912     LOG(ERROR) << "OnPrepareComplete prepare_async failed.";
913     if (IsValid(DemuxerStream::AUDIO))
914       GetRendererClient(DemuxerStream::AUDIO)
915           ->OnError(PIPELINE_ERROR_INITIALIZATION_FAILED);
916     else if (IsValid(DemuxerStream::VIDEO))
917       GetRendererClient(DemuxerStream::VIDEO)
918           ->OnError(PIPELINE_ERROR_INITIALIZATION_FAILED);
919     return;
920   }
921
922   if (GetPlayerState() != ESPLUSPLAYER_STATE_READY) {
923     LOG(ERROR) << "Invalid state (" << GetString(GetPlayerState())
924                << ") change during prepare. Returning.";
925     return;
926   }
927
928   LOG(INFO) << "(" << static_cast<void*>(this) << ") " << __func__
929             << " is_paused_ : " << is_paused_
930             << " seek_position : " << seek_position_
931             << " pending_seek_ : " << pending_seek_
932             << " pending_seek_position_ : " << pending_seek_position_;
933
934 #if defined(TIZEN_VIDEO_HOLE)
935   if (is_video_hole_)
936     video_plane_controller_->ResetMediaGeometry();
937 #endif
938
939   is_prepared_ = true;
940   if (pending_seek_) {
941     Seek(pending_seek_position_);
942   } else if (!is_paused_) {
943     Play();
944   }
945 }
946
947 void MediaPlayerESPlusPlayer::OnEos() {
948   if (!task_runner_->BelongsToCurrentThread()) {
949     task_runner_->PostTask(FROM_HERE,
950                            base::BindOnce(&MediaPlayerESPlusPlayer::OnEos,
951                                           weak_factory_.GetWeakPtr()));
952     return;
953   }
954
955   LOG(INFO) << "(" << static_cast<void*>(this) << ") " << __func__;
956   if (IsValid(DemuxerStream::VIDEO))
957     GetRendererClient(DemuxerStream::VIDEO)->OnEnded();
958   else if (IsValid(DemuxerStream::AUDIO))
959     GetRendererClient(DemuxerStream::AUDIO)->OnEnded();
960   Release();
961 }
962
963 void MediaPlayerESPlusPlayer::OnFrameReady(
964     const esplusplayer_decoded_video_packet* packet) {
965   if (!task_runner_->BelongsToCurrentThread()) {
966     task_runner_->PostTask(
967         FROM_HERE, base::BindOnce(&MediaPlayerESPlusPlayer::OnFrameReady,
968                                   weak_factory_.GetWeakPtr(), packet));
969     return;
970   }
971   tbm_surface_info_s suf_info = {
972       0,
973   };
974   tbm_surface_h tbm_surface = static_cast<tbm_surface_h>(packet->surface_data);
975
976   if (TBM_SURFACE_ERROR_NONE != tbm_surface_get_info(tbm_surface, &suf_info)) {
977     LOG(ERROR) << "|tbm_surface_get_info| failed";
978     return;
979   }
980
981   int width = static_cast<int>(suf_info.width);
982   int height = static_cast<int>(suf_info.height);
983   gfx::Size size(width, height);
984
985   base::TimeDelta timestamp = base::Milliseconds(packet->pts);
986   DLOG(INFO) << "(" << static_cast<void*>(this) << ") " << __func__
987              << " size:" << size.ToString()
988              << ", timestamp:" << timestamp.InMilliseconds()
989              << ", duration:" << packet->duration << ", Player(" << esplayer_
990              << ", state:" << GetString(GetPlayerState());
991
992 #if defined(TIZEN_TBM_SUPPORT)
993   gfx::TbmBufferHandle tbm_handle;
994   tbm_handle.tbm_surface = reinterpret_cast<uint64_t>(tbm_surface);
995   tbm_handle.media_packet = reinterpret_cast<uint64_t>(packet);
996   tbm_handle.player_id = player_id_;
997   tbm_handle.width = width;
998   tbm_handle.height = height;
999   data_cb_.Run(0, tbm_handle, timestamp);
1000 #else
1001   base::UnsafeSharedMemoryRegion shared_memory;
1002   uint32_t shared_memory_size =
1003       suf_info.planes[0].size + (suf_info.planes[0].size / 2);
1004   shared_memory = base::UnsafeSharedMemoryRegion::Create(shared_memory_size);
1005   if (!shared_memory.IsValid()) {
1006     LOG(ERROR) << "Shared Memory creation failed.";
1007     return;
1008   }
1009
1010   base::WritableSharedMemoryMapping memory_mapping;
1011   memory_mapping = shared_memory.Map();
1012   if (!memory_mapping.IsValid()) {
1013     LOG(ERROR) << "Shared Memory handle could not be obtained";
1014     return;
1015   }
1016
1017   unsigned char* y_ptr = static_cast<unsigned char*>(memory_mapping.memory());
1018
1019   // Video format will always be converted to I420
1020   switch (suf_info.format) {
1021     case TBM_FORMAT_NV12: {
1022       unsigned char* u_ptr = y_ptr + suf_info.planes[0].size;
1023       unsigned char* v_ptr = u_ptr + (suf_info.planes[0].size / 4);
1024       libyuv::NV12ToI420(suf_info.planes[0].ptr, suf_info.planes[0].stride,
1025                          suf_info.planes[1].ptr, suf_info.planes[1].stride,
1026                          y_ptr, suf_info.planes[0].stride, u_ptr,
1027                          suf_info.planes[1].stride / 2, v_ptr,
1028                          suf_info.planes[1].stride / 2, suf_info.width,
1029                          suf_info.height);
1030       break;
1031     }
1032     case TBM_FORMAT_YUV420: {
1033       unsigned char* u_ptr = y_ptr + suf_info.planes[0].size;
1034       unsigned char* v_ptr = u_ptr + suf_info.planes[1].size;
1035       libyuv::I420Copy(
1036           suf_info.planes[0].ptr, suf_info.planes[0].stride,
1037           suf_info.planes[1].ptr, suf_info.planes[1].stride,
1038           suf_info.planes[2].ptr, suf_info.planes[2].stride, y_ptr,
1039           suf_info.planes[0].stride, u_ptr, suf_info.planes[1].stride, v_ptr,
1040           suf_info.planes[2].stride, suf_info.width, suf_info.height);
1041       break;
1042     }
1043     default: {
1044       NOTIMPLEMENTED();
1045       LOG(WARNING) << "Not supported format";
1046       return;
1047     }
1048   }
1049   if (!sink_) {
1050     esplusplayer_decoded_buffer_destroy(
1051         esplayer_, const_cast<esplusplayer_decoded_video_packet*>(packet));
1052     data_cb_.Run(0, std::move(shared_memory), shared_memory_size, timestamp,
1053                  width, height);
1054   } else {
1055     uint8_t* const yuv_buffer = static_cast<uint8_t*>(memory_mapping.memory());
1056     scoped_refptr<VideoFrame> video_frame = VideoFrame::CreateFrame(
1057         media::PIXEL_FORMAT_I420, size, gfx::Rect(size), size, timestamp);
1058
1059     uint8_t* video_buf = yuv_buffer;
1060     const uint c_frm_size = shared_memory_size / 6;
1061     const uint y_frm_size = c_frm_size << 2;  // * 4;
1062
1063     // U Plane buffer.
1064     uint8_t* video_buf_u = video_buf + y_frm_size;
1065
1066     // V Plane buffer.
1067     uint8_t* video_buf_v = video_buf_u + c_frm_size;
1068
1069     libyuv::I420Copy(
1070         video_buf, video_frame.get()->stride(VideoFrame::kYPlane), video_buf_u,
1071         video_frame.get()->stride(VideoFrame::kYPlane) / 2, video_buf_v,
1072         video_frame.get()->stride(VideoFrame::kYPlane) / 2,
1073         video_frame.get()->GetWritableVisibleData(VideoFrame::kYPlane),
1074         video_frame.get()->stride(VideoFrame::kYPlane),
1075         video_frame.get()->GetWritableVisibleData(VideoFrame::kUPlane),
1076         video_frame.get()->stride(VideoFrame::kUPlane),
1077         video_frame.get()->GetWritableVisibleData(VideoFrame::kVPlane),
1078         video_frame.get()->stride(VideoFrame::kVPlane), width, height);
1079     esplusplayer_decoded_buffer_destroy(
1080         esplayer_, const_cast<esplusplayer_decoded_video_packet*>(packet));
1081
1082     sink_->PaintSingleFrame(video_frame);
1083   }
1084 #endif
1085 }
1086
1087 void MediaPlayerESPlusPlayer::OnFlushComplete() {
1088   NOTIMPLEMENTED();
1089 }
1090
1091 void MediaPlayerESPlusPlayer::OnReadyToSeek(
1092     const esplusplayer_stream_type stream_type,
1093     const uint64_t seek_time) {
1094   if (!task_runner_->BelongsToCurrentThread()) {
1095     task_runner_->PostTask(
1096         FROM_HERE,
1097         base::BindOnce(&MediaPlayerESPlusPlayer::OnReadyToSeek,
1098                        weak_factory_.GetWeakPtr(), stream_type, seek_time));
1099     return;
1100   }
1101   LOG(INFO) << "(" << static_cast<void*>(this) << ") " << __func__ << " : "
1102             << DemuxerStream::GetTypeName(GetDemuxerStreamType(stream_type))
1103             << " : " << seek_time;
1104
1105   SetShouldFeed(GetDemuxerStreamType(stream_type), true);
1106   SetIsEos(GetDemuxerStreamType(stream_type), false);
1107   ReadBuffer(GetDemuxerStreamType(stream_type));
1108 }
1109
1110 void MediaPlayerESPlusPlayer::OnSeekComplete() {
1111   if (!task_runner_->BelongsToCurrentThread()) {
1112     task_runner_->PostTask(
1113         FROM_HERE, base::BindOnce(&MediaPlayerESPlusPlayer::OnSeekComplete,
1114                                   weak_factory_.GetWeakPtr()));
1115     return;
1116   }
1117
1118   LOG(INFO) << "(" << static_cast<void*>(this) << ") " << __func__
1119             << " is_paused:" << is_paused_;
1120
1121   current_position_ = seek_position_;
1122   is_seeking_ = false;
1123   seek_position_ = base::TimeDelta();
1124   if (pending_seek_) {
1125     Seek(pending_seek_position_);
1126     pending_seek_position_ = base::TimeDelta();
1127     return;
1128   }
1129
1130   if (!is_paused_)
1131     Play();
1132 }
1133
1134 void MediaPlayerESPlusPlayer::OnResourceConflict() {
1135   if (!task_runner_->BelongsToCurrentThread()) {
1136     task_runner_->PostTask(
1137         FROM_HERE, base::BindOnce(&MediaPlayerESPlusPlayer::OnResourceConflict,
1138                                   weak_factory_.GetWeakPtr()));
1139     return;
1140   }
1141
1142   LOG(INFO) << "(" << static_cast<void*>(this) << ") " << __func__;
1143   NOTIMPLEMENTED();
1144 }
1145
1146 void MediaPlayerESPlusPlayer::OnError(const esplusplayer_error_type error) {
1147   if (!task_runner_->BelongsToCurrentThread()) {
1148     task_runner_->PostTask(FROM_HERE,
1149                            base::BindOnce(&MediaPlayerESPlusPlayer::OnError,
1150                                           weak_factory_.GetWeakPtr(), error));
1151     return;
1152   }
1153
1154   LOG(INFO) << "(" << static_cast<void*>(this) << ") " << __func__ << " : "
1155             << esplusplayer_get_error_string(
1156                    static_cast<esplusplayer_error_type>(error));
1157
1158   if (IsValid(DemuxerStream::VIDEO))
1159     GetRendererClient(DemuxerStream::VIDEO)->OnError(GetPipelineError(error));
1160   else if (IsValid(DemuxerStream::AUDIO))
1161     GetRendererClient(DemuxerStream::AUDIO)->OnError(GetPipelineError(error));
1162   Release();
1163 }
1164
1165 MediaPlayerESPlusPlayer::ElementryStream&
1166 MediaPlayerESPlusPlayer::GetElementryStream(DemuxerStream::Type type) {
1167   return elementry_stream_[GetElementryStreamIndex(type)];
1168 }
1169
1170 const MediaPlayerESPlusPlayer::ElementryStream&
1171 MediaPlayerESPlusPlayer::GetElementryStream(DemuxerStream::Type type) const {
1172   return elementry_stream_[GetElementryStreamIndex(type)];
1173 }
1174
1175 bool MediaPlayerESPlusPlayer::IsValid(DemuxerStream::Type type) const {
1176   return GetElementryStream(type).is_valid_;
1177 }
1178
1179 void MediaPlayerESPlusPlayer::SetIsValid(DemuxerStream::Type type, bool value) {
1180   GetElementryStream(type).is_valid_ = value;
1181 }
1182
1183 bool MediaPlayerESPlusPlayer::IsEos(DemuxerStream::Type type) const {
1184   return GetElementryStream(type).is_eos_;
1185 }
1186
1187 void MediaPlayerESPlusPlayer::SetIsEos(DemuxerStream::Type type, bool value) {
1188   GetElementryStream(type).is_eos_ = value;
1189 }
1190
1191 bool MediaPlayerESPlusPlayer::ShouldFeed(DemuxerStream::Type type) const {
1192   return GetElementryStream(type).should_feed_;
1193 }
1194
1195 void MediaPlayerESPlusPlayer::SetShouldFeed(DemuxerStream::Type type,
1196                                             bool value) {
1197   GetElementryStream(type).should_feed_ = value;
1198 }
1199
1200 bool MediaPlayerESPlusPlayer::ReadRequested(DemuxerStream::Type type) const {
1201   return GetElementryStream(type).read_requested_;
1202 }
1203
1204 void MediaPlayerESPlusPlayer::SetReadRequested(DemuxerStream::Type type,
1205                                                bool value) {
1206   GetElementryStream(type).read_requested_ = value;
1207 }
1208
1209 BufferStatus MediaPlayerESPlusPlayer::GetBufferStatus(
1210     DemuxerStream::Type type) {
1211   return GetElementryStream(type).buffer_status_;
1212 }
1213
1214 void MediaPlayerESPlusPlayer::SetBufferStatus(DemuxerStream::Type type,
1215                                               BufferStatus status) {
1216   GetElementryStream(type).buffer_status_ = status;
1217 }
1218
1219 DemuxerStream* MediaPlayerESPlusPlayer::GetDemuxerStream(
1220     DemuxerStream::Type type) const {
1221   return GetElementryStream(type).input_stream_;
1222 }
1223
1224 void MediaPlayerESPlusPlayer::SetDemuxerStream(DemuxerStream::Type type,
1225                                                DemuxerStream* stream) {
1226   GetElementryStream(type).input_stream_ = stream;
1227 }
1228
1229 RendererClient* MediaPlayerESPlusPlayer::GetRendererClient(
1230     DemuxerStream::Type type) const {
1231   return GetElementryStream(type).renderer_client_;
1232 }
1233
1234 void MediaPlayerESPlusPlayer::SetRendererClient(DemuxerStream::Type type,
1235                                                 RendererClient* client) {
1236   GetElementryStream(type).renderer_client_ = client;
1237 }
1238
1239 Queue& MediaPlayerESPlusPlayer::GetBufferQueue(DemuxerStream::Type type) {
1240   return GetElementryStream(type).pending_buffers_;
1241 }
1242
1243 void MediaPlayerESPlusPlayer::SetFrameAvailableCallback(
1244     const DataRequestCB& datacb) {
1245   data_cb_ = datacb;
1246 }
1247
1248 #if defined(TIZEN_VIDEO_HOLE)
1249 void MediaPlayerESPlusPlayer::SetVideoHole(bool is_video_hole) {
1250   LOG(INFO) << "(" << static_cast<void*>(this) << ") " << __func__
1251             << " is_video_hole : " << is_video_hole;
1252   is_video_hole_ = is_video_hole;
1253   if (is_video_hole_ && esplayer_ && !video_plane_controller_) {
1254     LOG(INFO) << "(" << static_cast<void*>(this) << ") " << __func__
1255               << " pended set video_plane_controller";
1256     video_plane_controller_.reset(
1257         new VideoPlaneControllerESPlusPlayer(esplayer_));
1258   }
1259 }
1260
1261 void MediaPlayerESPlusPlayer::SetMediaGeometry(const gfx::Rect& viewport_rect,
1262                                                const gfx::RectF& rect) {
1263   if (!is_video_hole_)
1264     return;
1265
1266   LOG(INFO) << __func__ << " viewport_rect: " << viewport_rect.ToString()
1267             << " rect : " << rect.ToString();
1268   video_plane_controller_->SetMediaGeometry(viewport_rect, rect);
1269 }
1270
1271 #endif
1272
1273 }  // namespace media