Skip to content

HTTPS clone URL

Subversion checkout URL

You can clone with
or
.
Download ZIP

Loading…

Simple video preview (HTML5 <video> tag) #235

Closed
wants to merge 5 commits into from

5 participants

@CrazyMonster

Unfortunately it only works with the (rather limited) number of video formats that browser vendors chose to support (the only exception AFAIK is Safari that is able to play every format supported by QuickTime, which can be extended with plugins).

@EliaCereda EliaCereda referenced this pull request
Closed

HTML5 media player #161

@buzzworkers

could this be used to implement the dynamically around mp3/ogg files for example ?

@buzzworkers

is the audio preview already implemented then ? waw..i mean i think it's time i change my php script directory listing..

Yes it is... It only supports what the browser supports (see this: https://developer.mozilla.org/en-US/docs/HTML/Supported_media_formats) but besides that it works. Also, I hacked out this implementation in a couple of hours (basically I just copied preview-img.js and adapted it for video and audio files) for use on my private media server so don't use it for anything serious without checking... ;)

Also, there is a patch that you need to apply if you want to use it on mobile devices, look here: https://github.com/CrazyMonster/h5ai/tree/preview-vid-nopreload

I didn't push it together with the pull request because I'm not sure about it, I should improve it but I haven't had the time to do it yet. Merge it on top of the preview-vid branch if you want to use it.

@buzzworkers

i will try to use h5ai with your commits, not very sure how to proceed but i will try.

@CrazyMonster

Use these instructions to build it: https://github.com/lrsjng/h5ai#build and then install it like the normal version: http://larsjung.de/h5ai/

@buzzworkers

can't have makejs to compile...it's not even considered a command..

@CrazyMonster

it's possible that is not in your PATH, mine is installed in /usr/local/bin/makejs

@noogs

What is the status of the commits by CrazyMonster? I'd like to be able to try the video player.

@CrazyMonster

The video and audio preview works pretty good at the moment, I use it every day on my media server and it plays most files with no problem (obviously just what your browser supports, so don't try playing MP4 files in Firefox). Among the things it doesn't support are subtitles support and proper error handling (if your browser doesn't support a particular file you'll just get a black player instead of a proper message). Nothing that prevents you from using it for personal stuff...

@lrsjng lrsjng added the Feature label
@noogs

I have the video player working and it plays all the files I would expect it to. However there is no audio at all for any of them. Any ideas?

@CrazyMonster

That is strange... What format are they? Did you try and open the file directly in the browser (i.e. copy the URL of the video and paste it in the URL bar)? If you can't hear the audio even now then there's some problem with your browser, not with h5ai.

@mkskarch

@ noogs: I had the same problem with no sound in Firefox on Win7. The soulution was: 1) swithch on the system sounds in the "Mixer" (Run > "sndvol") and 2) Follow the instructions of http://www.youtube.com/watch?v=aHuYmhY-5-g

The problem was only related to the user account in win7. As admin everything worked fine.

@lrsjng lrsjng changed the title from Added simple video preview that uses the HTML5 <video> tag to Simple video preview (HTML5 <video> tag)
@lrsjng
Owner

Added audio and video preview, works best (maybe only) in Chrome for the moment.

@lrsjng lrsjng closed this
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
This page is out of date. Refresh to see the latest.
View
8 src/_h5ai/client/css/inc/preview-audio.less
@@ -0,0 +1,8 @@
+#pv-audio-audio {
+ position: absolute;
+
+ max-width: 100%;
+ max-height: 100%;
+
+ box-shadow: 0 0 8px 2px rgba(0, 0, 0, 0.3);
+}
View
13 src/_h5ai/client/css/inc/preview-vid.less
@@ -0,0 +1,13 @@
+#pv-vid-video {
+ position: absolute;
+
+ max-width: 100%;
+ max-height: 100%;
+
+ box-shadow: 0 0 8px 2px rgba(0, 0, 0, 0.3);
+}
+
+#pv-vid-video:-webkit-full-screen {
+ top: auto !important;
+ left: auto !important;
+}
View
2  src/_h5ai/client/css/styles.less
@@ -14,6 +14,8 @@
@import "inc/preview";
@import "inc/preview-img";
@import "inc/preview-txt";
+@import "inc/preview-vid";
+@import "inc/preview-audio";
@import "inc/notify";
@import "inc/content";
View
129 src/_h5ai/client/js/inc/ext/preview-audio.js
@@ -0,0 +1,129 @@
+
+modulejs.define('ext/preview-audio', ['_', '$', 'core/settings', 'core/event', 'ext/preview'], function (_, $, allsettings, event, preview) {
+
+ var settings = _.extend({
+ enabled: false,
+ types: []
+ }, allsettings['preview-audio']),
+
+ //Credits go to Thorben (http://stackoverflow.com/a/5539081)
+ formatSecondsToHMS = function (d) {
+ d = Number(d);
+
+ var h = Math.floor(d / 3600);
+ var m = Math.floor(d % 3600 / 60);
+ var s = Math.floor(d % 3600 % 60);
+ return ((h > 0 ? h + ":" : "") + (m > 0 ? (h > 0 && m < 10 ? "0" : "") + m + ":" : "0:") + (s < 10 ? "0" : "") + s);
+ },
+
+ preloadAudio = function (src, callback) {
+
+ var $audio = $('<audio/>')
+ .one('loadedmetadata', function () {
+
+ callback($audio);
+ // setTimeout(function () { callback($img); }, 1000); // for testing
+ })
+ .attr('preload', 'auto')
+ .attr('src', src);
+ },
+
+ onEnter = function (items, idx) {
+
+ var currentItems = items,
+ currentIdx = idx,
+ currentItem = items[idx],
+
+ onAdjustSize = function () {
+
+ var $content = $('#pv-content'),
+ $audio = $('#pv-audio-audio');
+
+ if ($audio.length) {
+
+ $audio.css({
+ 'left': '' + (($content.width()-$audio.width())*0.5) + 'px',
+ 'top': '' + (($content.height()-$audio.height())*0.5) + 'px'
+ });
+
+ preview.setLabels([
+ currentItem.label,
+ formatSecondsToHMS($audio[0].duration)
+ ]);
+ }
+ },
+
+ onIdxChange = function (rel) {
+
+ currentIdx = (currentIdx + rel + currentItems.length) % currentItems.length;
+ currentItem = currentItems[currentIdx];
+
+ var spinnerTimeout = setTimeout(function () { preview.showSpinner(true); }, 200);
+
+ preloadAudio(currentItem.absHref, function ($preloaded_audio) {
+
+ clearTimeout(spinnerTimeout);
+ preview.showSpinner(false);
+
+ $('#pv-content').fadeOut(100, function () {
+ $preloaded_audio.attr('controls', true);
+
+ $('#pv-content').empty().append($preloaded_audio.attr('id', 'pv-audio-audio')).fadeIn(200);
+
+ // small timeout, so $preloaded_audio is visible and therefore $preloaded_audio.width is available
+ setTimeout(function () {
+ onAdjustSize();
+
+ preview.setIndex(currentIdx + 1, currentItems.length);
+ preview.setRawLink(currentItem.absHref);
+ }, 10);
+ });
+ });
+ };
+
+ onIdxChange(0);
+ preview.setOnIndexChange(onIdxChange);
+ preview.setOnAdjustSize(onAdjustSize);
+ preview.enter();
+ },
+
+ initItem = function (item) {
+
+ if (item.$view && _.indexOf(settings.types, item.type) >= 0) {
+ item.$view.find('a').on('click', function (event) {
+
+ event.preventDefault();
+
+ var matchedEntries = _.compact(_.map($('#items .item'), function (item) {
+
+ item = $(item).data('item');
+ return _.indexOf(settings.types, item.type) >= 0 ? item : null;
+ }));
+
+ onEnter(matchedEntries, _.indexOf(matchedEntries, item));
+ });
+ }
+ },
+
+ onLocationChanged = function (item) {
+
+ _.each(item.content, initItem);
+ },
+
+ onLocationRefreshed = function (item, added, removed) {
+
+ _.each(added, initItem);
+ },
+
+ init = function () {
+
+ if (!settings.enabled) {
+ return;
+ }
+
+ event.sub('location.changed', onLocationChanged);
+ event.sub('location.refreshed', onLocationRefreshed);
+ };
+
+ init();
+});
View
120 src/_h5ai/client/js/inc/ext/preview-vid.js
@@ -0,0 +1,120 @@
+
+modulejs.define('ext/preview-vid', ['_', '$', 'core/settings', 'core/event', 'ext/preview'], function (_, $, allsettings, event, preview) {
+
+ var settings = _.extend({
+ enabled: false,
+ types: []
+ }, allsettings['preview-vid']),
+
+ preloadVid = function (src, callback) {
+
+ var $video = $('<video/>')
+ .one('loadedmetadata', function () {
+
+ callback($video);
+ // setTimeout(function () { callback($img); }, 1000); // for testing
+ })
+ .attr('preload', 'auto')
+ .attr('src', src);
+ },
+
+ onEnter = function (items, idx) {
+
+ var currentItems = items,
+ currentIdx = idx,
+ currentItem = items[idx],
+
+ onAdjustSize = function () {
+
+ var $content = $('#pv-content'),
+ $vid = $('#pv-vid-video');
+
+ if ($vid.length) {
+
+ $vid.css({
+ 'left': '' + (($content.width()-$vid.width())*0.5) + 'px',
+ 'top': '' + (($content.height()-$vid.height())*0.5) + 'px'
+ });
+
+ preview.setLabels([
+ currentItem.label,
+ '' + $vid[0].videoWidth + 'x' + $vid[0].videoHeight,
+ '' + (100 * $vid.width() / $vid[0].videoWidth).toFixed(0) + '%'
+ ]);
+ }
+ },
+
+ onIdxChange = function (rel) {
+
+ currentIdx = (currentIdx + rel + currentItems.length) % currentItems.length;
+ currentItem = currentItems[currentIdx];
+
+ var spinnerTimeout = setTimeout(function () { preview.showSpinner(true); }, 200);
+
+ preloadVid(currentItem.absHref, function ($preloaded_vid) {
+
+ clearTimeout(spinnerTimeout);
+ preview.showSpinner(false);
+
+ $('#pv-content').fadeOut(100, function () {
+ $preloaded_vid.attr('controls', true);
+
+ $('#pv-content').empty().append($preloaded_vid.attr('id', 'pv-vid-video')).fadeIn(200);
+
+ // small timeout, so $preloaded_vid is visible and therefore $preloaded_vid.width is available
+ setTimeout(function () {
+ onAdjustSize();
+
+ preview.setIndex(currentIdx + 1, currentItems.length);
+ preview.setRawLink(currentItem.absHref);
+ }, 10);
+ });
+ });
+ };
+
+ onIdxChange(0);
+ preview.setOnIndexChange(onIdxChange);
+ preview.setOnAdjustSize(onAdjustSize);
+ preview.enter();
+ },
+
+ initItem = function (item) {
+
+ if (item.$view && _.indexOf(settings.types, item.type) >= 0) {
+ item.$view.find('a').on('click', function (event) {
+
+ event.preventDefault();
+
+ var matchedEntries = _.compact(_.map($('#items .item'), function (item) {
+
+ item = $(item).data('item');
+ return _.indexOf(settings.types, item.type) >= 0 ? item : null;
+ }));
+
+ onEnter(matchedEntries, _.indexOf(matchedEntries, item));
+ });
+ }
+ },
+
+ onLocationChanged = function (item) {
+
+ _.each(item.content, initItem);
+ },
+
+ onLocationRefreshed = function (item, added, removed) {
+
+ _.each(added, initItem);
+ },
+
+ init = function () {
+
+ if (!settings.enabled) {
+ return;
+ }
+
+ event.sub('location.changed', onLocationChanged);
+ event.sub('location.refreshed', onLocationRefreshed);
+ };
+
+ init();
+});
View
1  src/_h5ai/client/js/inc/ext/preview.js
@@ -74,6 +74,7 @@ modulejs.define('ext/preview', ['_', '$', 'core/settings', 'core/resource', 'cor
onExit = function () {
$(window).off('keydown', onKeydown);
+ $('#pv-content').empty();
$('#pv-overlay').stop(true, true).fadeOut(200);
},
View
20 src/_h5ai/conf/options.json
@@ -256,6 +256,26 @@ Options
},
/*
+ Show a video preview on click.
+
+ - types: array of types
+ */
+ "preview-vid": {
+ "enabled": true,
+ "types": ["video"]
+ },
+
+ /*
+ Show an audio preview on click.
+
+ - types: array of types
+ */
+ "preview-audio": {
+ "enabled": true,
+ "types": ["audio"]
+ },
+
+ /*
Show QRCodes on hovering files.
- size: width and height in pixel
Something went wrong with that request. Please try again.