(function ($) { var defaults = { showTime: 800, offsetBottom: 0, offsetTopm: 50, onLoadBackEnd: function (index, dom) { }, onLoadBackStart: function (index, dom) { } }; var $lazyImgList = $(); function checkOffset() { var scrollTop = $(document).scrollTop(); var windowHeight = $(window).height(); $lazyImgList.each(function (index) { var $dom = $(this); if ($dom.attr("data-comp")) return; // Already processed var offsetTop = $dom.offset().top; // Check if image is in viewport (with some buffer) if (offsetTop - scrollTop + defaults.offsetTopm >= 0 && offsetTop - scrollTop < (windowHeight + defaults.offsetBottom)) { showImg($dom, index); } }); } function showImg($dom, index) { $dom.attr("data-comp", "true"); var src = $dom.attr("data-lazy-src"); defaults.onLoadBackStart(index, $dom); // Create a temporary image to preload var temp = new Image(); temp.onload = function() { // Prepare for transition $dom.css({ "opacity": 0, "transition": "opacity " + (defaults.showTime / 1000) + "s ease-in-out" }); // Swap source $dom.attr("src", src); // Force reflow to ensure transition triggers void $dom[0].offsetWidth; // Fade in $dom.css("opacity", 1); defaults.onLoadBackEnd(index, $dom); }; temp.onerror = function() { // On error, show anyway (maybe broken image icon) but ensure visible $dom.attr("src", src); $dom.css("opacity", 1); }; temp.src = src; } function init(setting) { defaults = $.extend(defaults, setting); // Auto-convert standard images to lazy load format // Exclude .blog-img (Header Avatar) to prevent visibility issues $("img").not(".blog-img").each(function() { var $this = $(this); // Only convert if not already converted and has a src if (!$this.attr("data-lazy-src") && $this.attr("src")) { $this.attr("data-lazy-src", $this.attr("src")); // Set placeholder $this.attr("src", "data:image/gif;base64,R0lGODlhAQABAIAAAP///wAAACH5BAEAAAAALAAAAAABAAEAAAICRAEAOw=="); } }); $lazyImgList = $("img[data-lazy-src]"); checkOffset(); // Debounced scroll handler could be better, but sticking to simple binding for now $(window).off("scroll.lazy").on("scroll.lazy resize.lazy", function() { checkOffset(); }); } function tryAgain() { // Re-initialize for new content init(defaults); } window.lazyLoadInit = init; window.lazyLoadAgain = tryAgain; })(jQuery);