【问题标题】:How to add CSS transitions to Automatic Slider?如何将 CSS 过渡添加到自动滑块?
【发布时间】:2023-12-31 17:58:01
【问题描述】:

我正在尝试为我的自动滑块应用“不透明度/向左滑动”,但我做不到。请帮我解决这个问题。

let images = ["images/a.jpg", "images/b.jpg", "images/c.jpg", "images/d.jpg", ];
let i = 0;

function changeImg() {
  document.querySelector("#slider img").src = images[i];
  if (i < images.length - 1) {
    i++;
  } else {
    i = 0;
  }
  setTimeout("changeImg()", 1000);

}
onload(changeImg());
#slider img {
  width: 100vw;
  height: 60vh;
  transition: opacity 2s ease-out;
}
<section id="slider">
  <img name="slide" width="400" height="200" />
</section>

【问题讨论】:

  • 对不起,为什么你能成功?你到底在哪里遇到问题?
  • 滑块工作正常,但当图像发生变化时,我想添加一些平滑过渡。所以我添加了这个“transition: opacity 2s ease-out;”但它不起作用。
  • 我看不到图像不透明度发生变化的任何地方,因此永远不会有任何过渡。顺便说一句,您将只能转换传入图像的不透明度,而不是传出图像,因为在任何时候只有一个地方可以显示图像。这就是你想要的吗?
  • 是的。请编写代码来实现它。

标签: javascript css slider


【解决方案1】:

最初的要求是让图像褪色并显示另一张。

这可以通过将图像放在另一个之上(绝对位置)和不透明度为 0 并在不透明度上设置过渡来实现。当它是一个特定的图像时,在它被设置为不透明度 0 并且新图像的不透明度设置为 1 之前会显示该图像。

let images = ["https://picsum.photos/id/1015/300/300", "https://picsum.photos/id/1016/200/300", "https://picsum.photos/id/1018/300/200.jpg", "https://picsum.photos/id/1022/400/300", ];
const slider = document.querySelector('#slider');
const imgEls = [];
images.forEach(image => {
  let imgEl = document.createElement('img');
  imgEl.src = image;
  imgEls.push(imgEl);
  slider.appendChild(imgEl);
});
let i = 0;

function changeImg() {
  imgEls[i].style.opacity = 0;
  if (i < images.length - 1) {
    i++;
  } else {
    i = 0;
  }
  imgEls[i].style.opacity = 1;
  setTimeout("changeImg()", 1000);
}
window.onload = changeImg;
#slider {
  width: 100vw;
  height: 60vh;
  position: relative;
  isplay: felx;
  justify-content: center;
  align-items: center;
}

#slider img {
  display: inline-block;
  width: 100vw;
  height: 60vh;
  object-fit: contain;
  transition: opacity 2s ease-out;
  opacity: 0;
  position: absolute;
  top: 0;
  left: 0;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<section id="slider">
  <https://*.com/questions/69870264/how-to-add-css-transitions-to-automatic-slider#img name="slide" width="400" height="200" />
</section>

虽然该动作似乎与 cmets 中讨论的内容相对应,但它并没有构成真正的“滑块”,而且问题还谈到了使用 CSS 向左滑动。

这个 sn-p 对问题的代码采取了一种稍微不同的方法,因为一旦使用 Javascript 完成了幻灯片的初始设置,其他一切都通过 CSS 完成。这样做的好处是,系统可以直接将动画交给 GPU,而无需在超时时中断回主程序。

每张图片都位于 100% 的左侧(即屏幕右侧),并且它的动画与另一张相同 - 移动到中心,等待然后向左移出 - 不透明度淡入淡出分别。然而,图像以交错的时间开始动画,因此滑动看起来是连续的。

const slider = document.querySelector('#slider');
const images = ["https://picsum.photos/id/1015/300/300", "https://picsum.photos/id/1016/200/300", "https://picsum.photos/id/1018/300/200", "https://picsum.photos/id/1022/400/300"];
let div;
let count = 0;
images.forEach(image => {
  div = document.createElement('div');
  div.style.animationDelay = (count * 2) + 's';
  count++;
  div.style.setProperty('--img', 'url(' + image + ')');
  slider.appendChild(div);
});
slider.style.setProperty('--n', count);
#slider {
  overflow: hidden;
  width: 100vw;
  height: 60vh;
  position: relative;
}

#slider div {
  width: 100%;
  height: 100%;
  position: absolute;
  left: 0;
  top: 0;
  opacity: 0;
  display: inline-block;
  background-size: contain;
  background-position: center center;
  background-repeat: no-repeat;
  background-image: var(--img);
  animation-name: slide;
  animation-iteration-count: infinite;
  animation-timing-function: linear;
  animation-duration: calc(var(--n) * 2s);
  animation-fill-mode: forwards;
}

@keyframes slide {
  0% {
    opacity: 0;
    transform: translateX(100vw);
  }
  12.5% {
    opacity: 1;
    transform: translateX(0);
  }
  25% {
    opacity: 1;
    transform: translateX(0);
  }
  37.5%,
  100% {
    opacity: 0;
    transform: translateX(-100vw);
  }
}
&lt;div id="slider"&gt;&lt;/div&gt;

请注意,关键帧设置假定为 4 张图像。 % 值将不得不更改更多或更少。不幸的是,CSS 不允许变量作为关键帧中的 % 值,因此 JS 会理想地找到图像的数量并创建正确的关键帧。

【讨论】:

  • 感谢您的回答,但这远远超出了我的理解。如果它是根据我提供的代码编写的,我会很高兴。
  • 可以根据您的原始代码完成一些您想要的工作。您可以保留它,因为它只是添加 JS 以将当前 img 的不透明度设置为 0,并将下一个设置为不透明度 1。然后您的转换将产生一些效果,但是您的代码确实受到了只有一个元素的限制在其中显示图像以制作任何类似于滑块的东西。
最近更新 更多