UNPKG

lightgallery

Version:

lightGallery is a feature-rich, modular JavaScript gallery plugin for building beautiful image and video galleries for the web and the mobile

409 lines 18.3 kB
"use strict"; /** * Video module for lightGallery * Supports HTML5, YouTube, Vimeo, wistia videos * * * @ref Wistia * https://wistia.com/support/integrations/wordpress(How to get url) * https://wistia.com/support/developers/embed-options#using-embed-options * https://wistia.com/support/developers/player-api * https://wistia.com/support/developers/construct-an-embed-code * http://jsfiddle.net/xvnm7xLm/ * https://developer.mozilla.org/en-US/docs/Web/HTML/Element/video * https://wistia.com/support/embed-and-share/sharing-videos * https://private-sharing.wistia.com/medias/mwhrulrucj * * @ref Youtube * https://developers.google.com/youtube/player_parameters#enablejsapi * https://developers.google.com/youtube/iframe_api_reference * https://developer.chrome.com/blog/autoplay/#iframe-delegation * * @ref Vimeo * https://stackoverflow.com/questions/10488943/easy-way-to-get-vimeo-id-from-a-vimeo-url * https://vimeo.zendesk.com/hc/en-us/articles/360000121668-Starting-playback-at-a-specific-timecode * https://vimeo.zendesk.com/hc/en-us/articles/360001494447-Using-Player-Parameters */ var __assign = (this && this.__assign) || function () { __assign = Object.assign || function(t) { for (var s, i = 1, n = arguments.length; i < n; i++) { s = arguments[i]; for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p)) t[p] = s[p]; } return t; }; return __assign.apply(this, arguments); }; Object.defineProperty(exports, "__esModule", { value: true }); var lg_video_settings_1 = require("./lg-video-settings"); var lg_events_1 = require("../../lg-events"); var lg_video_utils_1 = require("./lg-video-utils"); var Video = /** @class */ (function () { function Video(instance) { // get lightGallery core plugin instance this.core = instance; this.settings = __assign(__assign({}, lg_video_settings_1.videoSettings), this.core.settings); return this; } Video.prototype.init = function () { var _this = this; /** * Event triggered when video url found without poster * Append video HTML * Play if autoplayFirstVideo is true */ this.core.LGel.on(lg_events_1.lGEvents.hasVideo + ".video", this.onHasVideo.bind(this)); this.core.LGel.on(lg_events_1.lGEvents.posterClick + ".video", function () { var $el = _this.core.getSlideItem(_this.core.index); _this.loadVideoOnPosterClick($el); }); this.core.LGel.on(lg_events_1.lGEvents.slideItemLoad + ".video", this.onSlideItemLoad.bind(this)); // @desc fired immediately before each slide transition. this.core.LGel.on(lg_events_1.lGEvents.beforeSlide + ".video", this.onBeforeSlide.bind(this)); // @desc fired immediately after each slide transition. this.core.LGel.on(lg_events_1.lGEvents.afterSlide + ".video", this.onAfterSlide.bind(this)); }; /** * @desc Event triggered when a slide is completely loaded * * @param {Event} event - lightGalley custom event */ Video.prototype.onSlideItemLoad = function (event) { var _this = this; var _a = event.detail, isFirstSlide = _a.isFirstSlide, index = _a.index; // Should check the active slide as well as user may have moved to different slide before the first slide is loaded if (this.settings.autoplayFirstVideo && isFirstSlide && index === this.core.index) { // Delay is just for the transition effect on video load setTimeout(function () { _this.loadAndPlayVideo(index); }, 200); } // Should not call on first slide. should check only if the slide is active if (!isFirstSlide && this.settings.autoplayVideoOnSlide && index === this.core.index) { this.loadAndPlayVideo(index); } }; /** * @desc Event triggered when video url or poster found * Append video HTML is poster is not given * Play if autoplayFirstVideo is true * * @param {Event} event - Javascript Event object. */ Video.prototype.onHasVideo = function (event) { var _a = event.detail, index = _a.index, src = _a.src, html5Video = _a.html5Video, hasPoster = _a.hasPoster; if (!hasPoster) { // All functions are called separately if poster exist in loadVideoOnPosterClick function this.appendVideos(this.core.getSlideItem(index), { src: src, addClass: 'lg-object', index: index, html5Video: html5Video, }); // Automatically navigate to next slide once video reaches the end. this.gotoNextSlideOnVideoEnd(src, index); } }; /** * @desc fired immediately before each slide transition. * Pause the previous video * Hide the download button if the slide contains YouTube, Vimeo, or Wistia videos. * * @param {Event} event - Javascript Event object. * @param {number} prevIndex - Previous index of the slide. * @param {number} index - Current index of the slide */ Video.prototype.onBeforeSlide = function (event) { if (this.core.lGalleryOn) { var prevIndex = event.detail.prevIndex; this.pauseVideo(prevIndex); } }; /** * @desc fired immediately after each slide transition. * Play video if autoplayVideoOnSlide option is enabled. * * @param {Event} event - Javascript Event object. * @param {number} prevIndex - Previous index of the slide. * @param {number} index - Current index of the slide * @todo should check on onSlideLoad as well if video is not loaded on after slide */ Video.prototype.onAfterSlide = function (event) { var _this = this; var _a = event.detail, index = _a.index, prevIndex = _a.prevIndex; // Do not call on first slide var $slide = this.core.getSlideItem(index); if (this.settings.autoplayVideoOnSlide && index !== prevIndex) { if ($slide.hasClass('lg-complete')) { setTimeout(function () { _this.loadAndPlayVideo(index); }, 100); } } }; Video.prototype.loadAndPlayVideo = function (index) { var $slide = this.core.getSlideItem(index); var currentGalleryItem = this.core.galleryItems[index]; if (currentGalleryItem.poster) { this.loadVideoOnPosterClick($slide, true); } else { this.playVideo(index); } }; /** * Play HTML5, Youtube, Vimeo or Wistia videos in a particular slide. * @param {number} index - Index of the slide */ Video.prototype.playVideo = function (index) { this.controlVideo(index, 'play'); }; /** * Pause HTML5, Youtube, Vimeo or Wistia videos in a particular slide. * @param {number} index - Index of the slide */ Video.prototype.pauseVideo = function (index) { this.controlVideo(index, 'pause'); }; Video.prototype.getVideoHtml = function (src, addClass, index, html5Video) { var video = ''; var videoInfo = this.core.galleryItems[index] .__slideVideoInfo || {}; var currentGalleryItem = this.core.galleryItems[index]; var videoTitle = currentGalleryItem.title || currentGalleryItem.alt; videoTitle = videoTitle ? 'title="' + videoTitle + '"' : ''; var commonIframeProps = "allowtransparency=\"true\"\n frameborder=\"0\"\n scrolling=\"no\"\n allowfullscreen\n mozallowfullscreen\n webkitallowfullscreen\n oallowfullscreen\n msallowfullscreen"; if (videoInfo.youtube) { var videoId = 'lg-youtube' + index; var youTubeParams = lg_video_utils_1.getYouTubeParams(videoInfo, this.settings.youTubePlayerParams); var isYouTubeNoCookieURL = lg_video_utils_1.isYouTubeNoCookie(src); var youtubeURL = isYouTubeNoCookieURL ? '//www.youtube-nocookie.com/' : '//www.youtube.com/'; video = "<iframe allow=\"autoplay\" id=" + videoId + " class=\"lg-video-object lg-youtube " + addClass + "\" " + videoTitle + " src=\"" + youtubeURL + "embed/" + (videoInfo.youtube[1] + youTubeParams) + "\" " + commonIframeProps + "></iframe>"; } else if (videoInfo.vimeo) { var videoId = 'lg-vimeo' + index; var playerParams = lg_video_utils_1.getVimeoURLParams(this.settings.vimeoPlayerParams, videoInfo); video = "<iframe allow=\"autoplay\" id=" + videoId + " class=\"lg-video-object lg-vimeo " + addClass + "\" " + videoTitle + " src=\"//player.vimeo.com/video/" + (videoInfo.vimeo[1] + playerParams) + "\" " + commonIframeProps + "></iframe>"; } else if (videoInfo.wistia) { var wistiaId = 'lg-wistia' + index; var playerParams = lg_video_utils_1.param(this.settings.wistiaPlayerParams); playerParams = playerParams ? '?' + playerParams : ''; video = "<iframe allow=\"autoplay\" id=\"" + wistiaId + "\" src=\"//fast.wistia.net/embed/iframe/" + (videoInfo.wistia[4] + playerParams) + "\" " + videoTitle + " class=\"wistia_embed lg-video-object lg-wistia " + addClass + "\" name=\"wistia_embed\" " + commonIframeProps + "></iframe>"; } else if (videoInfo.html5) { var html5VideoMarkup = ''; for (var i = 0; i < html5Video.source.length; i++) { html5VideoMarkup += "<source src=\"" + html5Video.source[i].src + "\" type=\"" + html5Video.source[i].type + "\">"; } if (html5Video.tracks) { var _loop_1 = function (i) { var trackAttributes = ''; var track = html5Video.tracks[i]; Object.keys(track || {}).forEach(function (key) { trackAttributes += key + "=\"" + track[key] + "\" "; }); html5VideoMarkup += "<track " + trackAttributes + ">"; }; for (var i = 0; i < html5Video.tracks.length; i++) { _loop_1(i); } } var html5VideoAttrs_1 = ''; var videoAttributes_1 = html5Video.attributes || {}; Object.keys(videoAttributes_1 || {}).forEach(function (key) { html5VideoAttrs_1 += key + "=\"" + videoAttributes_1[key] + "\" "; }); video = "<video class=\"lg-video-object lg-html5 " + (this.settings.videojs && this.settings.videojsTheme ? this.settings.videojsTheme + ' ' : '') + " " + (this.settings.videojs ? ' video-js' : '') + "\" " + html5VideoAttrs_1 + ">\n " + html5VideoMarkup + "\n Your browser does not support HTML5 video.\n </video>"; } return video; }; /** * @desc - Append videos to the slide * * @param {HTMLElement} el - slide element * @param {Object} videoParams - Video parameters, Contains src, class, index, htmlVideo */ Video.prototype.appendVideos = function (el, videoParams) { var _a; var videoHtml = this.getVideoHtml(videoParams.src, videoParams.addClass, videoParams.index, videoParams.html5Video); el.find('.lg-video-cont').append(videoHtml); var $videoElement = el.find('.lg-video-object').first(); if (videoParams.html5Video) { $videoElement.on('mousedown.lg.video', function (e) { e.stopPropagation(); }); } if (this.settings.videojs && ((_a = this.core.galleryItems[videoParams.index].__slideVideoInfo) === null || _a === void 0 ? void 0 : _a.html5)) { try { return videojs($videoElement.get(), this.settings.videojsOptions); } catch (e) { console.error('lightGallery:- Make sure you have included videojs'); } } }; Video.prototype.gotoNextSlideOnVideoEnd = function (src, index) { var _this = this; var $videoElement = this.core .getSlideItem(index) .find('.lg-video-object') .first(); var videoInfo = this.core.galleryItems[index].__slideVideoInfo || {}; if (this.settings.gotoNextSlideOnVideoEnd) { if (videoInfo.html5) { $videoElement.on('ended', function () { _this.core.goToNextSlide(); }); } else if (videoInfo.vimeo) { try { // https://github.com/vimeo/player.js/#ended new Vimeo.Player($videoElement.get()).on('ended', function () { _this.core.goToNextSlide(); }); } catch (e) { console.error('lightGallery:- Make sure you have included //github.com/vimeo/player.js'); } } else if (videoInfo.wistia) { try { window._wq = window._wq || []; // @todo Event is gettign triggered multiple times window._wq.push({ id: $videoElement.attr('id'), onReady: function (video) { video.bind('end', function () { _this.core.goToNextSlide(); }); }, }); } catch (e) { console.error('lightGallery:- Make sure you have included //fast.wistia.com/assets/external/E-v1.js'); } } } }; Video.prototype.controlVideo = function (index, action) { var $videoElement = this.core .getSlideItem(index) .find('.lg-video-object') .first(); var videoInfo = this.core.galleryItems[index].__slideVideoInfo || {}; if (!$videoElement.get()) return; if (videoInfo.youtube) { try { $videoElement.get().contentWindow.postMessage("{\"event\":\"command\",\"func\":\"" + action + "Video\",\"args\":\"\"}", '*'); } catch (e) { console.error("lightGallery:- " + e); } } else if (videoInfo.vimeo) { try { new Vimeo.Player($videoElement.get())[action](); } catch (e) { console.error('lightGallery:- Make sure you have included //github.com/vimeo/player.js'); } } else if (videoInfo.html5) { if (this.settings.videojs) { try { videojs($videoElement.get())[action](); } catch (e) { console.error('lightGallery:- Make sure you have included videojs'); } } else { $videoElement.get()[action](); } } else if (videoInfo.wistia) { try { window._wq = window._wq || []; // @todo Find a way to destroy wistia player instance window._wq.push({ id: $videoElement.attr('id'), onReady: function (video) { video[action](); }, }); } catch (e) { console.error('lightGallery:- Make sure you have included //fast.wistia.com/assets/external/E-v1.js'); } } }; Video.prototype.loadVideoOnPosterClick = function ($el, forcePlay) { var _this = this; // check slide has poster if (!$el.hasClass('lg-video-loaded')) { // check already video element present if (!$el.hasClass('lg-has-video')) { $el.addClass('lg-has-video'); var _html = void 0; var _src = this.core.galleryItems[this.core.index].src; var video = this.core.galleryItems[this.core.index].video; if (video) { _html = typeof video === 'string' ? JSON.parse(video) : video; } var videoJsPlayer_1 = this.appendVideos($el, { src: _src, addClass: '', index: this.core.index, html5Video: _html, }); this.gotoNextSlideOnVideoEnd(_src, this.core.index); var $tempImg = $el.find('.lg-object').first().get(); // @todo make sure it is working $el.find('.lg-video-cont').first().append($tempImg); $el.addClass('lg-video-loading'); videoJsPlayer_1 && videoJsPlayer_1.ready(function () { videoJsPlayer_1.on('loadedmetadata', function () { _this.onVideoLoadAfterPosterClick($el, _this.core.index); }); }); $el.find('.lg-video-object') .first() .on('load.lg error.lg loadedmetadata.lg', function () { setTimeout(function () { _this.onVideoLoadAfterPosterClick($el, _this.core.index); }, 50); }); } else { this.playVideo(this.core.index); } } else if (forcePlay) { this.playVideo(this.core.index); } }; Video.prototype.onVideoLoadAfterPosterClick = function ($el, index) { $el.addClass('lg-video-loaded'); this.playVideo(index); }; Video.prototype.destroy = function () { this.core.LGel.off('.lg.video'); this.core.LGel.off('.video'); }; return Video; }()); exports.default = Video; //# sourceMappingURL=lg-video.js.map