summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authoryoshiki@chromium.org <yoshiki@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2014-07-18 19:22:01 +0000
committeryoshiki@chromium.org <yoshiki@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2014-07-18 19:22:01 +0000
commit94bd40d9c6ebea76c3d7bafd13704c86bd292ae8 (patch)
treea2e06dd55a1ebddb2fafec595bebb6910bcce953
parentf3c1e7f6222be7bf378e082c359f0a77c0350cae (diff)
downloadchromium_src-94bd40d9c6ebea76c3d7bafd13704c86bd292ae8.zip
chromium_src-94bd40d9c6ebea76c3d7bafd13704c86bd292ae8.tar.gz
chromium_src-94bd40d9c6ebea76c3d7bafd13704c86bd292ae8.tar.bz2
Video Player: Add a message which is shown on casting
This patch shows a message like "Playing on xxxx", andd adds the dummy video element which will be used to control the casting video. BUG=305511 TEST=none Review URL: https://codereview.chromium.org/397813004 git-svn-id: svn://svn.chromium.org/chrome/trunk/src@284180 0039d316-1c4b-4281-b951-d872f2087c98
-rw-r--r--chrome/app/chromeos_strings.grdp8
-rw-r--r--chrome/browser/chromeos/extensions/file_manager/private_api_strings.cc5
-rw-r--r--ui/file_manager/video_player/css/cast_menu.css1
-rw-r--r--ui/file_manager/video_player/css/header.css6
-rw-r--r--ui/file_manager/video_player/css/video_player.css46
-rw-r--r--ui/file_manager/video_player/images/100/cast_big.pngbin0 -> 541 bytes
-rw-r--r--ui/file_manager/video_player/images/200/cast_big.pngbin0 -> 1203 bytes
-rw-r--r--ui/file_manager/video_player/js/cast/cast_video_element.js114
-rw-r--r--ui/file_manager/video_player/js/video_player.js53
-rw-r--r--ui/file_manager/video_player/js/video_player_scripts.js1
-rw-r--r--ui/file_manager/video_player/video_player.html6
11 files changed, 231 insertions, 9 deletions
diff --git a/chrome/app/chromeos_strings.grdp b/chrome/app/chromeos_strings.grdp
index 6f59d02..6c9a0c4 100644
--- a/chrome/app/chromeos_strings.grdp
+++ b/chrome/app/chromeos_strings.grdp
@@ -980,6 +980,14 @@ Press any key to continue exploring.
Failed to retrieve space info
</message>
+<!-- Video Player -->
+ <message name="IDS_VIDEO_PLAYER_PLAY_THIS_COMPUTER" desc="Message of menu item which is shown at the top of the list of Chromecasts. This menuitem is to play the video on this computer (locally), intead of on TVs with Chromecast.">
+ This computer
+ </message>
+ <message name="IDS_VIDEO_PLAYER_PLAYING_ON" desc="Message is shown ahead of the name of the current chromecast which plays the video now. For example, if this message is 'Playing on' and the Chromecast name is 'Foocast', 'Playing on Foocast' is shown.">
+ Playing on
+ </message>
+
<!-- Imageburn Strings -->
<message name="IDS_CHECKING_FOR_UPDATES" desc="Notification for checking for update">
Checking for updates
diff --git a/chrome/browser/chromeos/extensions/file_manager/private_api_strings.cc b/chrome/browser/chromeos/extensions/file_manager/private_api_strings.cc
index b6c088c..1f0d12d 100644
--- a/chrome/browser/chromeos/extensions/file_manager/private_api_strings.cc
+++ b/chrome/browser/chromeos/extensions/file_manager/private_api_strings.cc
@@ -514,6 +514,11 @@ bool FileBrowserPrivateGetStringsFunction::RunSync() {
SET_STRING("DEVICE_HARD_UNPLUGGED_TITLE", IDS_DEVICE_HARD_UNPLUGGED_TITLE);
SET_STRING("DEVICE_HARD_UNPLUGGED_MESSAGE",
IDS_DEVICE_HARD_UNPLUGGED_MESSAGE);
+
+ // Video Player
+ SET_STRING("VIDEO_PLAYER_PLAY_THIS_COMPUTER",
+ IDS_VIDEO_PLAYER_PLAY_THIS_COMPUTER);
+ SET_STRING("VIDEO_PLAYER_PLAYING_ON", IDS_VIDEO_PLAYER_PLAYING_ON);
#undef SET_STRING
dict->SetBoolean("PDF_VIEW_ENABLED",
diff --git a/ui/file_manager/video_player/css/cast_menu.css b/ui/file_manager/video_player/css/cast_menu.css
index 42006d6..161fd52 100644
--- a/ui/file_manager/video_player/css/cast_menu.css
+++ b/ui/file_manager/video_player/css/cast_menu.css
@@ -25,4 +25,3 @@
.cast-menu > :not(hr):hover {
background-color: #eee;
}
-
diff --git a/ui/file_manager/video_player/css/header.css b/ui/file_manager/video_player/css/header.css
index 5a5b738..fa37d55 100644
--- a/ui/file_manager/video_player/css/header.css
+++ b/ui/file_manager/video_player/css/header.css
@@ -75,6 +75,12 @@
url(../images/200/cast_off.png) 2x);
}
+#video-player[casting] > .header > button.cast-button {
+ background-image: -webkit-image-set(
+ url(../images/100/cast_on.png) 1x,
+ url(../images/200/cast_on.png) 2x);
+}
+
#video-player > .header > button.cast-button.hidden {
display: none;
}
diff --git a/ui/file_manager/video_player/css/video_player.css b/ui/file_manager/video_player/css/video_player.css
index 693f86d..e514e00 100644
--- a/ui/file_manager/video_player/css/video_player.css
+++ b/ui/file_manager/video_player/css/video_player.css
@@ -36,6 +36,48 @@ video {
width: 100%;
}
+#video-player:not([casting]) > #cast-container {
+ display: none;
+}
+
+#cast-container {
+ height: 100%;
+ left: 0;
+ position: absolute;
+ top: 0;
+ width: 100%;
+}
+
+#cast-container > #cast-info {
+ background-image: -webkit-image-set(
+ url('../images/100/cast_big.png') 1x,
+ url('../images/200/cast_big.png') 2x);
+ background-position: 0 0;
+ background-repeat: no-repeat;
+ bottom: 70px;
+ height: 38px;
+ left: 40px;
+ opacity: 0.8;
+ padding: 5px 56px;
+ position: absolute;
+ z-index: 10;
+}
+
+#cast-container > #cast-info > .first-line {
+ color: #fff;
+ font-size: 12px;
+ font-weight: bold;
+ line-height: 14px;
+ text-transform: uppercase;
+}
+
+#cast-container > #cast-info > .second-line {
+ color: #fff;
+ font-size: 22px;
+ font-weight: bold;
+ line-height: 24px;
+}
+
#controls-wrapper {
-webkit-box-align: center;
-webkit-box-orient: horizontal;
@@ -52,11 +94,11 @@ video {
display: -webkit-box;
}
-#video-player:not([tools]) .tool {
+#video-player:not([tools]):not([casting]) .tool {
opacity: 0;
}
-#video-player:not([tools]) {
+#video-player:not([tools]):not([casting]) {
cursor: none;
}
diff --git a/ui/file_manager/video_player/images/100/cast_big.png b/ui/file_manager/video_player/images/100/cast_big.png
new file mode 100644
index 0000000..7703e20
--- /dev/null
+++ b/ui/file_manager/video_player/images/100/cast_big.png
Binary files differ
diff --git a/ui/file_manager/video_player/images/200/cast_big.png b/ui/file_manager/video_player/images/200/cast_big.png
new file mode 100644
index 0000000..8c52382
--- /dev/null
+++ b/ui/file_manager/video_player/images/200/cast_big.png
Binary files differ
diff --git a/ui/file_manager/video_player/js/cast/cast_video_element.js b/ui/file_manager/video_player/js/cast/cast_video_element.js
new file mode 100644
index 0000000..299fa2b
--- /dev/null
+++ b/ui/file_manager/video_player/js/cast/cast_video_element.js
@@ -0,0 +1,114 @@
+// Copyright 2014 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.
+
+'use strict';
+
+/**
+ * This class is the dummy class which has same interface as VideoElement. This
+ * behaves like VideoElement, and is used for making Chromecast player
+ * controlled instead of the true Video Element tag.
+ *
+ * @constructor
+ */
+function CastVideoElement() {
+ this.duration_ = null;
+ this.currentTime_ = null;
+ this.src_ = '';
+ this.volume_ = 100;
+}
+
+CastVideoElement.prototype = {
+ __proto__: cr.EventTarget.prototype,
+
+ /**
+ * Returns a parent node. This must always be null.
+ * @return {Element}
+ */
+ get parentNode() {
+ return null;
+ },
+
+ /**
+ * The total time of the video.
+ * @type {number}
+ */
+ get duration() {
+ return this.duration_;
+ },
+
+ /**
+ * The current timestamp of the video.
+ * @type {number}
+ */
+ get currentTime() {
+ return this.currentTime_;
+ },
+ set currentTime(currentTime) {
+ this.currentTime_ = currentTime;
+ },
+
+ /**
+ * If this video is pauses or not.
+ * @type {boolean}
+ */
+ get paused() {
+ return false;
+ },
+
+ /**
+ * If this video is ended or not.
+ * @type {boolean}
+ */
+ get ended() {
+ return false;
+ },
+
+ /**
+ * If this video is seelable or not.
+ * @type {boolean}
+ */
+ get seekable() {
+ return false;
+ },
+
+ /**
+ * Value of the volume
+ * @type {number}
+ */
+ get volume() {
+ return this.volume_;
+ },
+ set volume(volume) {
+ this.volume_ = volume;
+ },
+
+ /**
+ * Returns the source of the current video.
+ * @return {string}
+ */
+ get src() {
+ return this.src_;
+ },
+
+ /**
+ * Plays the video.
+ */
+ play: function() {
+ // TODO(yoshiki): Implement this.
+ },
+
+ /**
+ * Pauses the video.
+ */
+ pause: function() {
+ // TODO(yoshiki): Implement this.
+ },
+
+ /**
+ * Loads the video.
+ */
+ load: function() {
+ // TODO(yoshiki): Implement this.
+ },
+};
diff --git a/ui/file_manager/video_player/js/video_player.js b/ui/file_manager/video_player/js/video_player.js
index a8b5b81..81ba71b 100644
--- a/ui/file_manager/video_player/js/video_player.js
+++ b/ui/file_manager/video_player/js/video_player.js
@@ -135,6 +135,8 @@ function VideoPlayer() {
this.videos_ = null;
this.currentPos_ = 0;
+ this.currentCast_ = null;
+
Object.seal(this);
}
@@ -272,11 +274,24 @@ VideoPlayer.prototype.loadVideo_ = function(url, title, opt_callback) {
this.controls.inactivityWatcher.disabled = false;
this.controls.decodeErrorOccured = false;
- this.videoElement_ = document.createElement('video');
- document.querySelector('#video-container').appendChild(this.videoElement_);
- this.controls.attachMedia(this.videoElement_);
+ if (this.currentCast_) {
+ videoPlayerElement.setAttribute('casting', true);
+ this.videoElement_ = new CastVideoElement();
+ this.controls.attachMedia(this.videoElement_);
+
+ document.querySelector('#cast-name-label').textContent =
+ loadTimeData.getString('VIDEO_PLAYER_PLAYING_ON');;
+ document.querySelector('#cast-name').textContent = this.currentCast_.name;
+ } else {
+ videoPlayerElement.removeAttribute('casting');
+
+ this.videoElement_ = document.createElement('video');
+ document.querySelector('#video-container').appendChild(this.videoElement_);
+
+ this.controls.attachMedia(this.videoElement_);
+ this.videoElement_.src = url;
+ }
- this.videoElement_.src = url;
this.videoElement_.load();
if (opt_callback) {
@@ -304,7 +319,7 @@ VideoPlayer.prototype.playFirstVideo = function() {
*/
VideoPlayer.prototype.unloadVideo = function() {
// Detach the previous video element, if exists.
- if (this.videoElement_)
+ if (this.videoElement_ && this.videoElement_.parentNode)
this.videoElement_.parentNode.removeChild(this.videoElement_);
this.videoElement_ = null;
};
@@ -380,6 +395,19 @@ VideoPlayer.prototype.reloadCurrentVideo_ = function(opt_callback) {
};
/**
+ * Invokes when a menuitem in the cast menu is selected.
+ * @param {Object} cast Selected element in the list of casts.
+ */
+VideoPlayer.prototype.onCastSelected_ = function(cast) {
+ // If the selected item is same as the current item, do nothing.
+ if ((this.currentCast_ && this.currentCast_.name) === (cast && cast.name))
+ return;
+
+ this.currentCast_ = cast || null;
+ this.reloadCurrentVideo_();
+};
+
+/**
* Set the list of casts.
* @param {Array.<Object>} casts List of casts.
*/
@@ -388,14 +416,27 @@ VideoPlayer.prototype.setCastList = function(casts) {
var menu = document.querySelector('#cast-menu');
menu.innerHTML = '';
+ // TODO(yoshiki): Handle the case that the current cast disapears.
+
if (casts.length === 0) {
button.classList.add('hidden');
+ if (!this.currentCast_) {
+ this.currentCast_ = null;
+ this.reloadCurrentVideo_();
+ }
return;
}
+ var item = new cr.ui.MenuItem();
+ item.label = loadTimeData.getString('VIDEO_PLAYER_PLAY_THIS_COMPUTER');
+ item.addEventListener('activate', this.onCastSelected_.wrap(this, null));
+ menu.appendChild(item);
+
for (var i = 0; i < casts.length; i++) {
var item = new cr.ui.MenuItem();
- item.textContent = casts[i].name;
+ item.label = casts[i].name;
+ item.addEventListener('activate',
+ this.onCastSelected_.wrap(this, casts[i]));
menu.appendChild(item);
}
button.classList.remove('hidden');
diff --git a/ui/file_manager/video_player/js/video_player_scripts.js b/ui/file_manager/video_player/js/video_player_scripts.js
index c8fe05d..ce1ef65 100644
--- a/ui/file_manager/video_player/js/video_player_scripts.js
+++ b/ui/file_manager/video_player/js/video_player_scripts.js
@@ -32,6 +32,7 @@
//<include src="../../file_manager/foreground/js/media/mouse_inactivity_watcher.js"/>
//<include src="cast/cast_extension_discoverer.js"/>
+//<include src="cast/cast_video_element.js"/>
//<include src="cast/load_cast_extension_api.js"/>
//<include src="cast/caster.js"/>
diff --git a/ui/file_manager/video_player/video_player.html b/ui/file_manager/video_player/video_player.html
index 1331e96..1dc8335 100644
--- a/ui/file_manager/video_player/video_player.html
+++ b/ui/file_manager/video_player/video_player.html
@@ -22,6 +22,12 @@
<body>
<div id="video-player" tools>
<menu id='cast-menu' class='cast-menu tool'></menu>
+ <div id="cast-container">
+ <div id="cast-info">
+ <div class="first-line" id='cast-name-label'></div>
+ <div class="second-line" id="cast-name"></div>
+ </div>
+ </div>
<div id="video-container">
</div>
<div id="header-container" class="header tool">