JSFiddle - React, Tailwind, and code Playground

by Daniel Mason

HTML

<script src="https://www.youtube.com/player_api"></script>
<ul>
    <li class="preview">
        <div class="carousel-slide" style="background-image: url('http://mischief-web-test.s3-eu-west-1.amazonaws.com/files/carousel/000/000/005/1430927707_FjFzG_ThatsNoMoon.jpg')">
            <div class="slide-background">
                <iframe id="slide-video-5" src="https://www.youtube.com/embed/BhP2BK_clk8?autoplay=0&amp;controls=0&amp;disablekb=1&amp;fs=0&amp;iv_load_policy=3&amp;loop=1&amp;modestbranding=1&amp;enablejsapi=1&amp;playsinline=1&amp;rel=0&amp;showinfo=0"></iframe>
            </div>
            <div class="slide-content">YouTube &lt;iframe&gt;</div>
        </div>
    </li>
    <li class="preview">
        <div class="carousel-slide" style="background-image: url('http://mischief-web-test.s3-eu-west-1.amazonaws.com/files/carousel/000/000/009/1431100031_cAPcC_2369524.png')">
            <div class="slide-background">
                <video src="http://mischief-web-test.s3-eu-west-1.amazonaws.com/files/carousel/000/000/009/1431100038_cd2Zf_MOV_0708.mp4" autoplay="autoplay" loop="loop" muted="muted"></video>
            </div>
            <div class="slide-content">HTML5 &lt;video&gt;</div>
        </div>
    </li>
</ul>

CSS

.preview {
    display: block;
    overflow: hidden;
    list-style: none;
    width: 215px;
    height: 160px;
    padding: 0;
    margin: 0;
    border: 0;
}

.carousel-slide {
    position: relative;
    width: 100%;
    height: 100%;
    background-size: cover;
    background-position: center;
    color: white;
    font-family: Raleway, sans-serif;
    overflow: hidden;
}

.carousel-slide video, .carousel-slide iframe {
    position: absolute;
    object-fit: cover;
    left: 50%;
    top: 50%;
    transform: translateX(-50%) translateY(-50%);
    border: 0;
    padding: 0;
    margin: 0;
}

.carousel-slide iframe {
    width: 320px;
    height: 240px;
}

.carousel-slide video {
    width: 100%;
    height: auto;
    min-width: 100%;
    min-height: 100%;
}

.carousel-slide .slide-content {
    z-index: 100;
    position: absolute;
    top: 0;
    left: 0;
    color: white;
    font-size: 1.5em;
    font-family: monospace;
}

JavaScript

var prepareYouTubeVideo = function (iFrame) {

    var $iFrame = $(iFrame),
        $parent = $iFrame.closest('.carousel-slide');

    var player = new YT.Player(iFrame.id, {
        events: {
            onReady: function () {
                player.mute();
                player.playVideo();
            },
            onStateChange: function (e) {
                if (e.data === YT.PlayerState.ENDED) {
                    player.playVideo();
                }
            },
            onError: function () {
                $(iFrame).remove();
            }
        }
    });

    // Resize the iFrame when the parent changes size
    var calculateSize = function(iFrame) {
        var $iFrame = $(iFrame),
            $parent = $iFrame.closest('.carousel-slide');
        
        var desiredAspectRatio = 16 / 9,
            actualAspectRatio = $parent.width() / $parent.height();

        if (actualAspectRatio >= desiredAspectRatio) { // wider
            $iFrame.width($parent.width());
            $iFrame.height($iFrame.width() / desiredAspectRatio);
            return;
        }
        // taller
        $iFrame.height($parent.height());
        $iFrame.width($iFrame.height() * desiredAspectRatio);
    };
    $parent.resize(iFrame, calculateSize);
};

// Prepare "each" video
$('iframe').each(function () {
    prepareYouTubeVideo(this);
});

// To demonstrate resizing
var animation = function () {
    $('.preview')
        .animate({
        width: '400px'
    }, 1000)
        .animate({
        height: '300px'
    }, 1000)
        .animate({
        width: '215px'
    }, 1000)
        .animate({
        height: '160px'
    }, 1000, animation);
};
animation();