JT_Dylan
JT_Dylan

Reputation: 143

blueimp Gallery - lightbox - customize for images and HTML5 video

We're using blueimp for our gallery and have successfully implemented the slider to show both images and html5 videos with multiple sources using the approach below

Here is the div layer:

<div id="blueimp-video-carousel-gallery" class="blueimp-gallery blueimp-gallery-controls blueimp-gallery-carousel " data-start-slideshow="false">
 <div class="slides"></div>
 <h3 class="title"></h3>
 <a class="prev">‹</a> 
 <a class="next">›</a>
 <p class="description"></p>
</div>

Here is a snippet of the for loop that populates the slider:

if (_media_type == 'video') {
    item['title'] = "title";
    item['type'] = "video/*";
    item['poster'] = media_thumbnail;
    item['description'] = "description";
    item['sources'] = [{href: _media_url_hls, type: "application/x-mpegurl"}, {href: _media_url_web, type: "video/mp4"}];
} else {
    item['title'] = "title";
    item['type'] = "image/jpeg";
    item['poster'] = media_thumbnail;
    item['description'] = "description";
}
objArr.push(item); 

//// omitted for brevity

blueimp.Gallery(objArr, { container: '#blueimp-video-carousel-gallery', carousel: 'true', preloadRange: 2, transitionSpeed: 400});

Next we wanted to implement the lightbox so we tried the following:

<div id="links" class="links"></div>
<div id="blueimp-gallery" class="blueimp-gallery">
    <div class="slides"></div>
    <h3 class="title"></h3>
    <a class="prev">‹</a>
    <a class="next">›</a>
    <a class="close">×</a>
    <a class="play-pause"></a>
    <ol class="indicator"></ol>
</div>

javascript for loop:

var linksContainer = $('#links');
var linksContainerData='';

//omitted for brevity
//video
linksContainerData +='<a href="'+_media_url+'" title="..." data-gallery="" class="blueimp-gallery-thumb-anchor"><img src="'+_media_thumbnail+'" ></a>';

//image
linksContainerData +='<a href="'+_media_url+'" title="..." data-gallery="" class="blueimp-gallery-thumb-anchor"><img src="'+_media_thumbnail+'" ></a>';

//after loop
$(linksContainer).append(linksContainerData);

This works for images but fails to load the videos. We'd like to be able to use the lightbox but in the slider be able to play HTML5 HLS and MP4 videos.

I believe the onOpen and onSlide event callbacks could be used, we can access the data from a jascript array, but I'm not sure how to customize.

Is it possible to specify a div layer instead of the 'a' tag so the slider uses a custom div layer?

Any guidance you an provide is greatly appreciated.

Regards, J

Upvotes: 1

Views: 2496

Answers (2)

Vadim
Vadim

Reputation: 1

I have a slider and when you click on a photo, the photo opens in a lightbox, for videos I solved this problem by replacing the img tag with video when changing the slide

 $(document).on('click', '[data-gallery]', function(event) {
    const list = $('a[data-gallery]');
    const index = $(this).data("index");
    let prevVideo = null;

    function onClickVideo(){
      const video = this;
      const isVideoPlaying = !!(video.currentTime > 0 && !video.paused && !video.ended && video.readyState > 2);      

      isVideoPlaying ? video?.pause() : video?.play();
    }

    Gallery(
      list,
      {
        videoContent: true,
        carousel: false,
        index,videoPlaysInline: true,
        onslide: function (indexSlide, slide) {
          prevVideo?.trigger?.('pause');
          prevVideo?.off?.('click',onClickVideo);
          const video = $('video', $(list[indexSlide])).clone();
          video.on('click',onClickVideo)
          $(slide).removeClass('slide-loading');
          $(slide).removeClass('slide-error');
          $(slide).html(video);
          prevVideo = video;
          $(video).attr('autoplay', true);
          $(video).attr('playsinline', true);
          $(video).attr('controls',true);
          $(video).attr('poster', "");
          $(video).css({
            width:"100%",
            height:"100%"
          });
          video[0].play();
        },
      }
    );
  })

example html code

<a 
  href="{}" 
  data-type="video/mp4"
  data-index="1"
>
  <video style="max-width: 100%; max-height: 100%;" poster=" 
  {}">
    <source src="{}" type="video/mp4"/>
    Your browser does not support the video tag.
  </video>
</a>

Upvotes: 0

JT_Dylan
JT_Dylan

Reputation: 143

I was able to get the light box to work with an onClick that opens the carousel with a single entry and works with images and video; video has playback in hls with mp4 fallback.

I found the solution with the help of these links: https://blueimp.github.io/Gallery/ (see source) https://blueimp.github.io/Gallery/js/jquery.blueimp-gallery.js (note: global click handler)

So I ended up with this function:

$(document).on('click', '[data-gallery]', function(event) {
    var id = $(this).data('gallery');
    var widget = $(id);
    var selected_media_id;
    var media_id;
    var obj;
    selected_media_id = widget.selector;
    console.log("objArr.length-->"+objArr.length);
    for (i=0; i<objArr.length; i++) {
    obj = objArr[i];
    if (selected_media_id == obj['title']) {
        break;
    }
    }
    return blueimp.Gallery([obj], { container : '#blueimp-gallery', carousel : true});
});

So I essentially fetch my identifier which is set in the attribute

data-gallery="identifier"

and loop through the array built as noted prior and then initialize the #blueimp-gallery with a single object wrapped in an array [obj]. Missing the [] threw me for a bit.

So now the onclick in the light box opens the modal with a single entry with an x to close which will work well enough for now. For videos it opens with a poster background and play icon and plays hls in Mac Safari and mp4 in chrome.

The video controls are not great (basic player controls) and there is room for improvement but this does the basics of what I wanted to achieve.

Hope this helps.

-J

Upvotes: 0

Related Questions