diff --git a/src/webui/extjs.c b/src/webui/extjs.c
index 6b6b9ade..c7d21a74 100755
--- a/src/webui/extjs.c
+++ b/src/webui/extjs.c
@@ -165,6 +165,7 @@ extjs_root(http_connection_t *hc, const char *remain, void *opaque)
extjs_load(hq, "static/app/config.js");
extjs_load(hq, "static/app/tvhlog.js");
extjs_load(hq, "static/app/status.js");
+ extjs_load(hq, "static/tv.js");
/**
* Finally, the app itself
diff --git a/src/webui/static/app/dvr.js b/src/webui/static/app/dvr.js
index ee19b4d8..58caff7b 100644
--- a/src/webui/static/app/dvr.js
+++ b/src/webui/static/app/dvr.js
@@ -67,9 +67,8 @@ tvheadend.dvrDetails = function(entry) {
if (entry.url != null && entry.filesize > 0) {
content += '
';
+ + parseInt(entry.filesize / 1000000) + ' MB';
+
}
var win = new Ext.Window({
diff --git a/src/webui/static/app/epg.js b/src/webui/static/app/epg.js
index 9b4a65c4..caa3639e 100755
--- a/src/webui/static/app/epg.js
+++ b/src/webui/static/app/epg.js
@@ -54,12 +54,6 @@ tvheadend.epgDetails = function(event) {
content += '' + event.ext_text + '
';
content += ''
-
- now = new Date();
- if (event.start < now && event.end > now) {
- content += "";
- }
-
content += '';
content += '';
@@ -483,7 +477,7 @@ tvheadend.epg = function() {
text : 'Watch TV',
iconCls : 'eye',
handler : function() {
- new tvheadend.VLC();
+ new tvheadend.VideoPlayer();
}
},
'-',
diff --git a/src/webui/static/app/ext.css b/src/webui/static/app/ext.css
index b1a2f4f8..124dfbc5 100644
--- a/src/webui/static/app/ext.css
+++ b/src/webui/static/app/ext.css
@@ -333,6 +333,27 @@
padding: 10px;
}
+.tv-video-player {
+ margin-right: auto;
+ margin-left : auto;
+
+ width : 100%;
+ height: 100%;
+ background: black;
+ color: white;
+}
+
+.tv-video-idle {
+ background-image : url(../../docresources/tvheadendlogo.png);
+ background-repeat : no-repeat;
+ background-position : center;
+}
+
+.tv-video-message {
+ text-align: center;
+ font-size: 150%;
+}
+
.about-title {
font-size: 24px;
font-weight: bold;
diff --git a/src/webui/static/app/tvheadend.js b/src/webui/static/app/tvheadend.js
index 2fe9ec87..6effc4f5 100644
--- a/src/webui/static/app/tvheadend.js
+++ b/src/webui/static/app/tvheadend.js
@@ -50,192 +50,155 @@ Ext.Ajax.request({
});
/**
- * Displays a mediaplayer using VLC plugin
+ * Displays a mediaplayer using the html5 video element
*/
-tvheadend.VLC = function(url) {
+tvheadend.VideoPlayer = function(url) {
- var vlc = Ext.get(document.createElement('embed'));
- vlc.set({
- type : 'application/x-vlc-plugin',
- pluginspage : 'http://www.videolan.org',
- version : 'VideoLAN.VLCPlugin.2',
- width : '100%',
- height : '100%',
- autoplay : 'no'
- });
+ var videoPlayer = new tv.ui.VideoPlayer({
+ params: {
+ resolution: 384
+ }
+ });
- var vlcPanel = new Ext.Panel({
- border : false,
- layout : 'fit',
- bodyStyle : 'background: transparent;',
- contentEl: vlc
- });
-
- var missingPlugin = Ext.get(document.createElement('div'));
- var missingPluginPanel = new Ext.Panel({
- border : false,
- layout : 'fit',
- bodyStyle : 'background: transparent;',
- contentEl : missingPlugin
- });
-
- var selectChannel = new Ext.form.ComboBox({
- loadingText : 'Loading...',
- width : 200,
- displayField : 'name',
- store : tvheadend.channels,
- mode : 'local',
- editable : false,
- triggerAction : 'all',
- emptyText : 'Select channel...'
- });
+ var selectChannel = new Ext.form.ComboBox({
+ loadingText : 'Loading...',
+ width : 200,
+ displayField : 'val',
+ store : tvheadend.channels,
+ mode : 'local',
+ editable : false,
+ triggerAction : 'all',
+ emptyText : 'Select channel...'
+ });
- selectChannel.on('select', function(c, r) {
- var streamurl = 'stream/channelid/' + r.data.chid;
- var playlisturl = 'playlist/channelid/' + r.data.chid;
+ selectChannel.on('select', function(c, r) {
+ videoPlayer.zapTo(r.id);
+ });
- if (!vlc.dom.playlist || vlc.dom.playlist == 'undefined') {
- var html = 'Embedded player could not be started.
You are probably missing VLC Mozilla plugin for your browser.
';
- html += 'M3U Playlist
';
- html += 'Direct URL
';
- missingPlugin.dom.innerHTML = html;
- missingPluginPanel.show();
- vlcPanel.hide();
+ var slider = new Ext.Slider({
+ width : 135,
+ height : 20,
+ value : 90,
+ increment : 1,
+ minValue : 0,
+ maxValue : 100
+ });
+
+ var sliderLabel = new Ext.form.Label();
+ sliderLabel.setText("90%");
+ slider.addListener('change', function() {
+ videoPlayer.setVolume(slider.getValue());
+ sliderLabel.setText(videoPlayer.getVolume() + '%');
+ });
+
+ var selectResolution = new Ext.form.ComboBox({
+ width: 150,
+ displayField:'name',
+ valueField: 'res',
+ value: 384,
+ mode: 'local',
+ editable: false,
+ triggerAction: 'all',
+ emptyText: 'Select resolution...',
+ store: new Ext.data.SimpleStore({
+ fields: ['res','name'],
+ id: 0,
+ data: [
+ ['288','288p'],
+ ['384','384p'],
+ ['480','480p'],
+ ['576','576p']
+ ]
+ })
+ });
+
+ selectResolution.on('select', function(c, r) {
+ videoPlayer.setResolution(r.data.res);
+ if(videoPlayer.isIdle())
+ return;
+
+ var index = selectChannel.selectedIndex;
+ if(index < 0)
+ return;
+
+ var ch = selectChannel.getStore().getAt(index);
+ videoPlayer.zapTo(ch.id);
+ });
+
+ var win = new Ext.Window({
+ title : 'Live TV Player',
+ layout : 'fit',
+ width : 682 + 14,
+ height : 384 + 56,
+ constrainHeader : true,
+ iconCls : 'eye',
+ resizable : true,
+ tbar : [
+ selectChannel,
+ '-',
+ {
+ iconCls : 'control_play',
+ tooltip : 'Play',
+ handler : function() {
+ if(!videoPlayer.isIdle()) { //probobly paused
+ videoPlayer.play();
+ return;
+ }
+
+ var index = selectChannel.selectedIndex;
+ if(index < 0)
+ return;
+
+ var ch = selectChannel.getStore().getAt(index);
+ videoPlayer.zapTo(ch.id);
}
- else {
- vlc.dom.playlist.stop();
- vlc.dom.playlist.items.clear();
- vlc.dom.playlist.add(streamurl);
- vlc.dom.playlist.playItem(0);
- vlc.dom.audio.volume = slider.getValue();
- missingPluginPanel.hide();
- vlcPanel.show();
+ },
+ {
+ iconCls : 'control_pause',
+ tooltip : 'Pause',
+ handler : function() {
+ videoPlayer.pause();
}
- });
-
- var slider = new Ext.Slider({
- width : 135,
- height : 20,
- value : 90,
- increment : 1,
- minValue : 0,
- maxValue : 100
- });
-
- var sliderLabel = new Ext.form.Label();
- sliderLabel.setText("90%");
- slider.addListener('change', function() {
- if (vlc.dom.playlist && vlc.dom.playlist.isPlaying) {
- vlc.dom.audio.volume = slider.getValue();
- sliderLabel.setText(vlc.dom.audio.volume + '%');
+ },
+ {
+ iconCls : 'control_stop',
+ tooltip : 'Stop',
+ handler : function() {
+ videoPlayer.stop();
}
- else {
- sliderLabel.setText(slider.getValue() + '%');
+ },
+ '-',
+ {
+ iconCls : 'control_fullscreen',
+ tooltip : 'Fullscreen',
+ handler : function() {
+ videoPlayer.fullscreen();
}
- });
+ },
+ '-',
+ selectResolution,
+ '-',
+ {
+ iconCls : 'control_volume',
+ tooltip : 'Volume',
+ disabled : true
+ }, ],
+ items : [videoPlayer]
+ });
+
+ win.on('beforeShow', function() {
+ win.getTopToolbar().add(slider);
+ win.getTopToolbar().add(new Ext.Toolbar.Spacer());
+ win.getTopToolbar().add(new Ext.Toolbar.Spacer());
+ win.getTopToolbar().add(new Ext.Toolbar.Spacer());
+ win.getTopToolbar().add(sliderLabel);
+ });
+
+ win.on('close', function() {
+ videoPlayer.stop();
+ });
- var win = new Ext.Window({
- title : 'VLC Player',
- layout : 'fit',
- width : 507 + 14,
- height : 384 + 56,
- constrainHeader : true,
- iconCls : 'eye',
- resizable : true,
- tbar : [
- selectChannel,
- '-',
- {
- iconCls : 'control_play',
- tooltip : 'Play',
- handler : function() {
- if (vlc.dom.playlist && vlc.dom.playlist.items.count
- && !vlc.dom.playlist.isPlaying) {
- vlc.dom.playlist.play();
- }
- }
- },
- {
- iconCls : 'control_pause',
- tooltip : 'Pause',
- handler : function() {
- if (vlc.dom.playlist && vlc.dom.playlist.items.count) {
- vlc.dom.playlist.togglePause();
- }
- }
- },
- {
- iconCls : 'control_stop',
- tooltip : 'Stop',
- handler : function() {
- if (vlc.dom.playlist) {
- vlc.dom.playlist.stop();
- }
- }
- },
- '-',
- {
- iconCls : 'control_fullscreen',
- tooltip : 'Fullscreen',
- handler : function() {
- if (vlc.dom.playlist && vlc.dom.playlist.isPlaying
- && (vlc.dom.VersionInfo.substr(0, 3) != '1.1')) {
- vlc.dom.video.toggleFullscreen();
- }
- else if (vlc.dom.VersionInfo.substr(0, 3) == '1.1') {
- alert('Fullscreen mode is broken in VLC 1.1.x');
- }
- }
- }, '-', {
- iconCls : 'control_volume',
- tooltip : 'Volume',
- disabled : true
- }, ],
- items : [ vlcPanel, missingPluginPanel ]
- });
-
- win.on('beforeShow', function() {
- win.getTopToolbar().add(slider);
- win.getTopToolbar().add(new Ext.Toolbar.Spacer());
- win.getTopToolbar().add(new Ext.Toolbar.Spacer());
- win.getTopToolbar().add(new Ext.Toolbar.Spacer());
- win.getTopToolbar().add(sliderLabel);
-
- // check if vlc plugin wasn't initialised correctly
- if (!vlc.dom.playlist || (vlc.dom.playlist == 'undefined')) {
- vlc.dom.style.display = 'none';
- var html = 'Embedded player could not be started.
You are probably missing VLC Mozilla plugin for your browser.
';
-
- if (url) {
- var channelid = url.substr(url.lastIndexOf('/'));
- var streamurl = 'stream/channelid/' + channelid;
- var playlisturl = 'playlist/channelid/' + channelid;
- html += 'M3U Playlist
';
- html += 'Direct URL
';
- }
- missingPlugin.dom.innerHTML = html;
- vlcPanel.hide();
- }
- else {
- // check if the window was opened with an url-parameter
- if (url) {
- vlc.dom.playlist.items.clear();
- vlc.dom.playlist.add(url);
- vlc.dom.playlist.playItem(0);
-
- //enable yadif2x deinterlacer for vlc > 1.1
- var point1 = vlc.dom.VersionInfo.indexOf('.');
- var point2 = vlc.dom.VersionInfo.indexOf('.', point1 + 1);
- var majVersion = vlc.dom.VersionInfo.substring(0, point1);
- var minVersion = vlc.dom.VersionInfo.substring(point1 + 1, point2);
- if ((majVersion >= 1) && (minVersion >= 1))
- vlc.dom.video.deinterlace.enable("yadif2x");
- }
- missingPluginPanel.hide();
- }
- });
-
- win.show();
+ win.show();
};
/**
diff --git a/src/webui/static/tv.js b/src/webui/static/tv.js
index b17e7915..37155768 100644
--- a/src/webui/static/tv.js
+++ b/src/webui/static/tv.js
@@ -137,16 +137,15 @@ tv.ui.VideoPlayer = Ext.extend(Ext.Panel, (function() {
render: {
fn: function() {
this.message = this.body.createChild({
- tag : 'span',
+ tag : 'div',
cls : 'tv-video-message',
- hidden: true,
html: ''
});
+ this.message.setVisibilityMode(Ext.Element.DISPLAY);
+ this.message.hide();
this.video = this.body.createChild({
tag : 'video',
- width : '100%',
- height : '100%',
html : "Your browser doesn't support html5 video"
});
@@ -255,6 +254,43 @@ tv.ui.VideoPlayer = Ext.extend(Ext.Panel, (function() {
this.video.dom.load();
},
+ pause: function() {
+ this.video.dom.pause();
+ },
+
+ setVolume: function(vol) {
+ this.video.dom.volume = vol / 100.0;
+ },
+
+ getVolume: function() {
+ return Math.round(100 * this.video.dom.volume);
+ },
+
+ setDisplaySize: function(width, height) {
+ this.video.setSize(width, height);
+ },
+
+ setResolution: function(res) {
+ this.params.resolution = res;
+ },
+
+ isIdle: function() {
+ return this.body.hasClass('tv-video-idle');
+ },
+
+ fullscreen: function() {
+ var dom = this.video.dom;
+
+ if(typeof dom.requestFullScreen !== 'undefined')
+ dom.requestFullScreen();
+
+ else if(typeof dom.mozRequestFullScreen !== 'undefined')
+ dom.mozRequestFullScreen();
+
+ else if(typeof dom.webkitRequestFullScreen !== 'undefined')
+ dom.webkitEnterFullscreen();
+ },
+
play: function() {
this.message.hide();
this.body.removeClass('tv-video-loading');
@@ -412,6 +448,7 @@ tv.app = function() {
},
renderTo: Ext.getBody()
});
+ videoPlayer.setDisplaySize('100%', '00%');
var chList = new tv.ui.ChannelList({
store: new Ext.data.JsonStore({