我一直在使用 jQuery 3.1.1 制作我自己的 JavaScript 幻灯片。它工作正常,但由于某种原因,过渡动画不流畅。当只有两张照片时,它工作正常,但一旦我添加了第三张照片,它就完全不能正常工作了。
我做了这个 fiddle ,如果有人能提供一些见解,我将不胜感激。
!function($) {
"use strict";
$.slideshow = function(container) {
let $container = $(container);
let children = $container.find('.slide').length;
$container.find('.slide').each(function(index) {
let zIndex = 210 - index;
let bg = $(this).data('bg');
$(this).css('background-image', 'url(' + bg + ')');
});
let settings = {
'transition': 500,
'delay': 6000,
};
let currentSlide = 0;
$.fn.showNext = function() {
let nextSlide = ((currentSlide + 1) < children) ? (currentSlide + 1) : 0;
let $current = $container.find('.slide:nth-child(' + (currentSlide + 1) + ')');
let $next = $container.find('.slide:nth-child(' + (nextSlide + 1) + ')');
$current.animate({
'opacity': 0
}, settings.transition);
setTimeout(function() {
$current.css('z-index', 200);
$current.css('opacity', 1);
$next.css('z-index', 210);
}, settings.transition + 100);
console.log(currentSlide, nextSlide);
currentSlide = ((currentSlide + 1) < children) ? (currentSlide + 1) : 0;
setTimeout(function() {
$container.showNext();
}, settings.delay);
};
setTimeout(function() {
$container.showNext();
}, settings.delay);
};
}(jQuery);
$.slideshow('.slideshow');
.slideshow-wrapper {
height: 100vh;
overflow: hidden;
position: relative;
width: 100%;
}
.slideshow {
height: 100%;
position: relative;
width: 100%;
}
.slide {
background-position: center;
background-size: cover;
height: 100%;
left: 0;
overflow: hidden;
position: absolute;
top: 0;
width: 100%;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/3.1.1/jquery.min.js"></script>
<div class="slideshow-wrapper">
<div class="slideshow">
<div class="slide" data-bg="https://s3.amazonaws.com/StartupStockPhotos/uploads/20160503/6.jpg"></div>
<div class="slide" data-bg="https://s3.amazonaws.com/StartupStockPhotos/uploads/20160503/5.jpg"></div>
<div class="slide" data-bg="https://s3.amazonaws.com/StartupStockPhotos/uploads/20160503/4.jpg"></div>
</div>
</div>
最佳答案
jQuery 代码中存在多个问题。这是我的发现:
- 它正在运行 JavaScript 正在运行的竞争条件 在 HTML 有时间加载之前。没有初始的 div 标记已加载到文档对象中。容器分区 长度为 0。加载 0 毫秒的单个 setTimeout 将取消阻止并允许在 JS 运行之前加载 HTML。
- 第 3 张图片 (4.jpg) 第一张显示,而不是第 1 张图片 (6.jpg)。代码中更改了 z-index,但未将其应用回图像。
- “current”的不透明度正在动画化为 0,然后立即回升到 1。我认为您要将“next”的不透明度更改为 1,而不是将“current”的不透明度从 1 更改为 0,并且然后回到 1。
- 初始化过渡开始时很流畅,但随后重复动画往往会循环得更快,并在“下一个”图像出现之前淡出到白页。用户可能会发现动画以 6 秒的延迟开始,然后每张图像加速到 1/2 秒。后一个动画太快了。
- 动画是弹出而不是消失。它也没有使用交叉溶解,但我建议使用一个。我添加它是为了向您展示它是如何工作的。
- 代码似乎没有被清理,这就是为什么您遇到 console.log 的编码问题并被迫使用 $container 来更正它的原因。 container 变量在用(container) 作为参数传入后,不能用“let container = ...”重新声明。当我通过传入“选择器”参数名称更正它时,我可以删除容器变量上的 $。这有助于区分哪些代码与 jQuery 绑定(bind),哪些不绑定(bind)。
- 严重依赖于使用 setTimeout 方法,但正如您可能已经知道的那样......那些只运行 1x 然后停止。为了让它们连续循环,开始的 setTimeout 已更改为 setInterval。
试试这个 edited JS Fiddle ,它解决了这些问题。 顺便说一句,这是 jQuery .animate方法。
CSS 更改:
- 添加了“不透明度:0;”所有幻灯片。
- 添加了“不透明度:1;”到第一张幻灯片。
CSS:
.slideshow-wrapper {
height: 100vh;
overflow: hidden;
position: relative;
width: 100%;
}
.slideshow {
height: 100%;
position: relative;
width: 100%;
}
.slide {
background-position: center;
background-size: cover;
height: 100%;
left: 0;
opacity: 0; /* <-- New --- */
overflow: hidden;
position: absolute;
top: 0;
width: 100%;
}
.slide:first-child { /* <-- New --- */
opacity: 1;
}
JavaScript 有很多修改
!function($) {
"use strict";
$.slideshow = function(selector) {
let container = $(selector);
let children = container.find('.slide').length;
container.find('.slide').each(function(index) {
let zIndex = 210 - index;
$(this).css('z-index', zIndex); // <-- This was missing, as it was loading the last image as the 1st image.
let bg = $(this).data('bg');
$(this).css('background-image', 'url(' + bg + ')');
});
let settings = {
'delay': 2000
};
let currentSlide = 0;
$.fn.showNext = function() {
let nextSlide = ((currentSlide + 1) < children) ? (currentSlide + 1) : 0;
let current = container.find('.slide:nth-child(' + (currentSlide + 1) + ')');
let next = container.find('.slide:nth-child(' + (nextSlide + 1) + ')');
next.animate({
'opacity': 1,
'z-index': 210
}, settings.transition);
// Creates the Cross-Dissolve, as 1 image "next" is fadding up from opacity 0 to 1, while current is fadding down from 1 to 0.
current.animate({
'opacity': 0,
'z-index': 200
}, settings.transition);
};
// Starts the animation loop.
setInterval(function() {
container.showNext();
currentSlide = ((currentSlide + 1) < children) ? (currentSlide + 1) : 0;
}, settings.delay);
};
}(jQuery);
setTimeout(function() {
$.slideshow('.slideshow');
}, 0); // Fixes the race condition, by allowing the HTML to load before the JS runs.
HTML - 没有变化,但在使用 jsfiddle 时删除了脚本标签
<script src="https://ajax.googleapis.com/ajax/libs/jquery/3.1.1/jquery.min.js"></script>
<div class="slideshow-wrapper">
<div class="slideshow">
<div class="slide" data-bg="https://s3.amazonaws.com/StartupStockPhotos/uploads/20160503/6.jpg"></div>
<div class="slide" data-bg="https://s3.amazonaws.com/StartupStockPhotos/uploads/20160503/5.jpg"></div>
<div class="slide" data-bg="https://s3.amazonaws.com/StartupStockPhotos/uploads/20160503/4.jpg"></div>
</div>
</div>
玩得开心 edited JS Fiddle进一步自定义它!
关于JavaScript 幻灯片放映不流畅,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/41405840/