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

Side by Side Diff: chrome/browser/media/android/remote/remote_media_player_manager.cc

Issue 928643003: Upstream Chrome for Android Cast. (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Created 5 years, 10 months 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 unified diff | Download patch
OLDNEW
(Empty)
1 // Copyright 2013 The Chromium Authors. All rights reserved.
whywhat 2015/02/25 16:31:32 Do we want to update the year in the added files,
aberent 2015/03/10 18:46:47 I don't think so. Copyright normally is about the
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 "chrome/browser/media/android/remote/remote_media_player_manager.h"
whywhat 2015/02/25 16:31:32 insert a blank line after the class header file
aberent 2015/03/11 18:29:58 Done.
6 #include "chrome/browser/android/tab_android.h"
7 #include "chrome/common/chrome_content_client.h"
8 #include "content/common/media/media_player_messages_android.h"
9 #include "third_party/skia/include/core/SkBitmap.h"
10 #include "ui/gfx/android/java_bitmap.h"
11
12 using media::MediaPlayerAndroid;
13
14 namespace remote_media {
15
16 RemoteMediaPlayerManager::RemoteMediaPlayerManager(
17 content::RenderFrameHost* render_frame_host)
18 : BrowserMediaPlayerManager(render_frame_host),
19 weak_ptr_factory_(this) {
20 }
21
22 RemoteMediaPlayerManager::~RemoteMediaPlayerManager() {}
23
24 void RemoteMediaPlayerManager::OnStart(int player_id) {
25 if (MaybeStartPlayingRemotely(player_id))
26 return;
27
28 ReplaceRemotePlayerWithLocal();
29 BrowserMediaPlayerManager::OnStart(player_id);
30 }
31
32 void RemoteMediaPlayerManager::OnInitialize(
33 const MediaPlayerHostMsg_Initialize_Params& media_params) {
34 BrowserMediaPlayerManager::OnInitialize(media_params);
35
36 MediaPlayerAndroid* player = GetPlayer(media_params.player_id);
37 if (player) {
38 CreateRemoteMediaPlayer(player);
39 RemoteMediaPlayerBridge* remote_player = GetRemotePlayer(
40 media_params.player_id);
41 if (remote_player)
42 remote_player->OnPlayerCreated();
43 }
44 }
45
46 void RemoteMediaPlayerManager::OnDestroyPlayer(int player_id) {
47 RemoteMediaPlayerBridge* player = GetRemotePlayer(player_id);
48 if (player)
49 player->OnPlayerDestroyed();
50 BrowserMediaPlayerManager::OnDestroyPlayer(player_id);
51 }
52
53 void RemoteMediaPlayerManager::OnReleaseResources(int player_id) {
54 // We only want to release resources of local players.
55 if (player_id != RemotePlayerId())
56 BrowserMediaPlayerManager::OnReleaseResources(player_id);
57 }
58
59 void RemoteMediaPlayerManager::OnRequestRemotePlayback(int player_id) {
60 RemoteMediaPlayerBridge* player = GetRemotePlayer(player_id);
61 if (player)
62 player->RequestRemotePlayback();
63 }
64
65 void RemoteMediaPlayerManager::OnRequestRemotePlaybackControl(int player_id) {
66 RemoteMediaPlayerBridge* player = GetRemotePlayer(player_id);
67 if (player)
68 player->RequestRemotePlaybackControl();
69 }
70
71 int RemoteMediaPlayerManager::GetTabId() {
72 if (!web_contents())
73 return -1;
74
75 TabAndroid* tab = TabAndroid::FromWebContents(web_contents());
76 if (!tab)
77 return -1;
78
79 return tab->GetAndroidId();
80 }
81
82 void RemoteMediaPlayerManager::OnSetPoster(int player_id, const GURL& url) {
83 RemoteMediaPlayerBridge* player = GetRemotePlayer(player_id);
84
85 if (player && url.is_empty()) {
86 player->SetPosterBitmap(std::vector<SkBitmap>());
87 } else {
88 // TODO(aberent) OnSetPoster is called when the attributes of the video
89 // element are parsed, which may be before OnInitialize is called. We are
90 // here relying on the image fetch taking longer than the delay until
91 // OnInitialize is called, and hence the player is created. This is not
92 // guaranteed.
93 content::WebContents::ImageDownloadCallback callback = base::Bind(
94 &RemoteMediaPlayerManager::DidDownloadPoster,
95 weak_ptr_factory_.GetWeakPtr(), player_id);
96 web_contents()->DownloadImage(
97 url,
98 false, // is_favicon, false so that cookies will be used.
99 0, // max_bitmap_size, 0 means no limit.
100 callback);
101 }
102 }
103
104 void RemoteMediaPlayerManager::DidDownloadPoster(
105 int player_id,
106 int id,
107 int http_status_code,
108 const GURL& image_url,
109 const std::vector<SkBitmap>& bitmaps,
110 const std::vector<gfx::Size>& original_bitmap_sizes) {
111 RemoteMediaPlayerBridge* player = GetRemotePlayer(player_id);
112 if (player)
113 player->SetPosterBitmap(bitmaps);
114 }
115
116 RemoteMediaPlayerBridge* RemoteMediaPlayerManager::CreateRemoteMediaPlayer(
117 MediaPlayerAndroid* local_player) {
118 RemoteMediaPlayerBridge* player = new RemoteMediaPlayerBridge(
119 local_player,
120 GetUserAgent(),
121 false,
122 this);
123 remote_players_.push_back(player);
124 player->Initialize();
125 return player;
126 }
127
128 int RemoteMediaPlayerManager::RemotePlayerId() {
129 // The remote player is created with the same id as the corresponding local
130 // player.
131 if (replaced_local_player_.get()) {
132 return replaced_local_player_->player_id();
133 } else {
134 return -1;
135 }
136 }
137
138 void RemoteMediaPlayerManager::ReplaceLocalPlayerWithRemote(
139 MediaPlayerAndroid* player) {
140 if (!player)
141 return;
142
143 int player_id = player->player_id();
144 if (player_id == RemotePlayerId()) {
145 // The player is already remote.
146 return;
147 }
148
149 // Before we replace the new remote player, put the old local player back
150 // in its place.
151 ReplaceRemotePlayerWithLocal();
152
153 // Pause the local player first before replacing it. This will allow the local
154 // player to reset its state, such as the PowerSaveBlocker.
155 // We have to pause locally as well as telling the renderer to pause, because
156 // by the time the renderer comes back to us telling us to pause we will have
157 // switched players.
158 player->Pause(true);
159 Send(new MediaPlayerMsg_DidMediaPlayerPause(RoutingID(), player_id));
160
161 // Find the remote player
162 for (auto it = remote_players_.begin(); it != remote_players_.end(); ++it) {
163 if ((*it)->player_id() == player_id) {
164 replaced_local_player_ = SwapPlayer(player_id, *it);
165
166 // Seek to the previous player's position.
167 (*it)->SeekTo(player->GetCurrentTime());
168
169 // SwapPlayers takes ownership, so we have to remove the remote player
170 // from the vector.
171 remote_players_.weak_erase(it);
172 break;
173 }
174 }
175 }
176
177 void RemoteMediaPlayerManager::ReplaceRemotePlayerWithLocal() {
178 int player_id = RemotePlayerId();
179 if (player_id == -1)
180 return;
181
182 Send(new MediaPlayerMsg_DidMediaPlayerPause(RoutingID(), player_id));
183 Send(new MediaPlayerMsg_DisconnectedFromRemoteDevice(RoutingID(), player_id));
184
185 scoped_ptr<MediaPlayerAndroid> remote_player =
186 SwapPlayer(player_id, replaced_local_player_.release());
187 if (remote_player) {
188 // Seek to the previous player's position.
189 GetPlayer(player_id)->SeekTo(remote_player->GetCurrentTime());
190
191 remote_player->Release();
192 // Add the remote player back into the list
193 remote_players_.push_back(
194 static_cast<RemoteMediaPlayerBridge *>(remote_player.release()));
195 }
196 }
197
198 bool RemoteMediaPlayerManager::MaybeStartPlayingRemotely(int player_id) {
199 MediaPlayerAndroid* player = GetPlayer(player_id);
200 if (!player)
201 return false;
202
203 RemoteMediaPlayerBridge* remote_player = GetRemotePlayer(player_id);
204
205 if (!remote_player)
206 return false;
207
208 if (remote_player->IsMediaPlayableRemotely() &&
209 remote_player->IsRemotePlaybackAvailable() &&
210 remote_player->IsRemotePlaybackPreferredForFrame()) {
211 ReplaceLocalPlayerWithRemote(player);
212
213 remote_player->SetNativePlayer();
214 remote_player->Start();
215
216 Send(new MediaPlayerMsg_DidMediaPlayerPlay(RoutingID(), player_id));
217
218 Send(new MediaPlayerMsg_ConnectedToRemoteDevice(
219 RoutingID(),
220 player_id,
221 remote_player->GetCastingMessage()));
222
223 return true;
224 }
225
226 return false;
227 }
228
229 void RemoteMediaPlayerManager::OnRemoteDeviceSelected(int player_id) {
230
231 MediaPlayerAndroid* player = GetPlayer(player_id);
232 if (!player)
233 return;
234
235 if (MaybeStartPlayingRemotely(player_id))
236 return;
237 OnStart(player_id);
238 }
239
240 void RemoteMediaPlayerManager::OnRemoteDeviceUnselected(int player_id) {
241 if (player_id == RemotePlayerId())
242 ReplaceRemotePlayerWithLocal();
243 }
244
245 void RemoteMediaPlayerManager::OnRemotePlaybackFinished(int player_id) {
246 if (player_id == RemotePlayerId())
247 ReplaceRemotePlayerWithLocal();
248 }
249
250 void RemoteMediaPlayerManager::OnRouteAvailabilityChanged(
251 int player_id, bool routes_available) {
252 Send(
253 new MediaPlayerMsg_RemoteRouteAvailabilityChanged(RoutingID(), player_id,
254 routes_available));
255 }
256
257 void RemoteMediaPlayerManager::ReleaseFullscreenPlayer(
258 MediaPlayerAndroid* player) {
259 // Release the original player's resources, not the current fullscreen player
260 // (which is the remote player).
261 if (replaced_local_player_.get())
262 replaced_local_player_->Release();
263 else
264 BrowserMediaPlayerManager::ReleaseFullscreenPlayer(player);
265 }
266
267 void RemoteMediaPlayerManager::OnPlaying(int player_id) {
268 Send(new MediaPlayerMsg_DidMediaPlayerPlay(RoutingID(),player_id));
269 }
270
271 void RemoteMediaPlayerManager::OnPaused(int player_id) {
272 Send(new MediaPlayerMsg_DidMediaPlayerPause(RoutingID(),player_id));
273 }
274
275 RemoteMediaPlayerBridge* RemoteMediaPlayerManager::GetRemotePlayer(
276 int player_id) {
277 if (player_id == RemotePlayerId()) {
278 return static_cast<RemoteMediaPlayerBridge*>(GetPlayer(player_id));
279 } else {
280 for (RemoteMediaPlayerBridge* player : remote_players_) {
281 if (player->player_id() == player_id) {
282 return player;
283 }
284 }
285 return nullptr;
286 }
287 }
288
289 void RemoteMediaPlayerManager::OnMediaMetadataChanged(int player_id,
290 base::TimeDelta duration,
291 int width, int height,
292 bool success) {
293 if (player_id == RemotePlayerId() && replaced_local_player_.get()) {
294 Send(
295 new MediaPlayerMsg_MediaMetadataChanged(
296 RoutingID(), player_id, duration,
297 replaced_local_player_->GetVideoWidth(),
298 replaced_local_player_->GetVideoHeight(), success));
299 } else {
300 BrowserMediaPlayerManager::OnMediaMetadataChanged(player_id, duration,
301 width, height, success);
302 }
303 }
304 } // namespace remote_media
whywhat 2015/02/25 16:31:32 blank line before the namespace closing?
aberent 2015/03/11 18:29:58 Done.
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698