Browse Source

Move js and css code out of index

Joachim M. Giæver 4 years ago
parent
commit
c36862a103
2 changed files with 209 additions and 0 deletions
  1. 43 0
      alt-yt-player.css
  2. 166 0
      alt-yt-player.js

+ 43 - 0
alt-yt-player.css

@@ -0,0 +1,43 @@
+/**
+ * @Author: Joachim M. Giæver
+ * URL: https://git.giaever.org/Magy/alt-youtube-player
+ */
+
+/* 
+   Adapt to your needs,
+   but it shouldn't be necessary to add much of css
+   as the js-script will handle sizing.
+*/
+* {padding: 0;margin: 0;} /* Not necessary when using frameworks */
+
+.player {
+    position: relative;
+    z-index: 2;
+    width: 70vw;
+    margin: 0 auto;
+}
+
+/*
+   Note that the > restricts the img to be on the root level of .player
+*/
+.player > img.thumb {
+    position: absolute;
+    z-index: 1;
+    width: 100%;
+}
+
+.player > iframe {
+    position: absolute;
+    z-index: -1;
+    width: 100%;
+    height: 100%;
+}
+.player.play {
+    cursor: pointer;
+}
+.player.stop {
+    cursor: not-allowed;
+}
+.player.loading {
+    cursor: wait;
+}

+ 166 - 0
alt-yt-player.js

@@ -0,0 +1,166 @@
+/**
+ * @Author: Joachim M. Giæver
+ * URL: https://git.giaever.org/Magy/alt-youtube-player
+ */
+
+// Hack to load Youtube iframe_api
+jQuery.getScript("https://www.youtube.com/iframe_api")
+
+var ytd = $.Deferred();
+window.onYouTubeIframeAPIReady = function () {
+    ytd.resolve(window.YT);
+};
+
+$(document).ready(function () {
+    // Store all instances of «Youtube Players»
+    var ytp = [];
+
+    // Change effect on IN and OUT here.
+    // Will affect on both «playerOpen» and «playerClose»
+    $.fn.outEffect = $.fn.fadeOut;
+    $.fn.inEffect = $.fn.fadeIn;
+
+    // When a player opens
+    var playerOpen = function (i, player) {
+        if (!ytp[i])
+            return;
+        
+        // Remove thumb and show iframe
+        player.find('.thumb').outEffect();
+        player.find('iframe').inEffect({
+            complete: function () {
+                // When fully opened, plat video and change cursor
+                if (ytp[i].getPlayerState() != YT.PlayerState.PLAYING)
+                    ytp[i].playVideo()
+                player.removeClass('play loading').addClass('stop');
+            }
+        });
+
+        // Close all the players that might be open.
+        $('.player').each(function (idx) {
+            if (i == idx) return;
+            playerClose(idx, $(this));
+        })
+    }
+
+    // When a player is closing
+    var playerClose = function (i, player) {
+        if (!ytp[i])
+            return;
+
+        // Hide iframe and show thumg
+        player.find('iframe').outEffect()
+        player.find('.thumb').inEffect(function() {
+            // Stop the video; if playing
+            if (ytp[i].getPlayerState() == YT.PlayerState.PLAYING)
+                ytp[i].pauseVideo();
+
+            player.removeClass('stop loading').addClass('play');
+        });
+    }
+
+    // Make sure Iframe has the same size as the thumb-img
+    var adoptThumbSizeToIframe = function (player) {
+        var ytvid = player.find('iframe');
+        var thumb = player.find('.thumb');
+
+        var hidden = thumb.is(':hidden');
+
+        // Hack to read size
+        if (hidden)
+            thumb.show();
+
+        player.css({
+            height: thumb.height(),
+        });
+
+        // Adopt the size of the thumbnail to the iframe
+        ytvid.css({
+            height: thumb.height(),
+            width: thumb.width(),
+        });
+
+        if (hidden)
+            thumb.hide();
+
+    }
+
+    // On scroll, check that we are withing bounding. Close if not.
+    window.addEventListener('scroll', function (e) {
+        var w = Math.max(document.documentElement.clientWidth, window.innerWidth || 0);
+        var h = Math.max(document.documentElement.clientHeight, window.innerHeight || 0);
+        var d = $(document).scrollTop();
+
+        $('.player').each(function (i) {
+            if ($(this).find('iframe:visible').length == 0)
+                return; // player not open (already showing thumb)
+
+            var x = $(this).offset()['top']; 
+            var xoff = $(this).height() / 15;
+
+            if ((x + $(this).height() - xoff) < d || (x + xoff) > (d + h))
+                playerClose(i, $(this));
+
+            /*
+            No horizontal test... but...
+            var y = $(this).offset()['left'];
+            var yoff = ($(this).width() / 15);
+            */
+
+        })
+    })
+
+    window.addEventListener('resize', function () {
+        $('.player').each(function() {
+            console.log("Resize");
+            adoptThumbSizeToIframe($(this));
+        })
+    })
+
+    // Youtube API is reacy
+    ytd.done(function (YT) {
+        /*
+        Initialize player on all of them.
+        Could be optimized and wait with init until the player should start,
+        and destroy it when it's closed.
+        */
+        $(".player").each(function (i) {
+            var player = $(this).addClass('loading');
+            var ytvid = player.find('iframe').hide();
+            adoptThumbSizeToIframe(player);
+
+            // Generate and add id to the iframe
+            ytvid.attr('id', 'player-' + (i+1));
+            ytp.push(new YT.Player(ytvid.attr('id'), {
+                events: {
+                    'onReady': function (e) {
+                        player.removeClass('loading').addClass('play');
+                        player.bind('click', function () {
+                            playerOpen(i, player);
+                        })
+                    },
+                    'onStateChange': function (e) {
+                        // Add event specific data here
+                        switch (e.data) {
+                        case YT.PlayerState.ENDED:
+                            playerClose(i, player)
+                            break;
+                        case YT.PlayerState.PLAYING:
+                            // console.log("PLAYING");
+                            break;
+                        case YT.PlayerState.PAUSED:
+                            player.removeClass('stop loading').addClass('play');
+                            break;
+                        case YT.PlayerState.BUFFERING:
+                            player.removeClass('stop play').addClass('loading');
+                            break;
+                        case YT.PlayerState.CUED:
+                            //console.log("CUED");
+                            break;
+                        }
+                    }, 
+                }
+            }));
+        })
+    })
+});