成人免费xxxxx在线视频软件_久久精品久久久_亚洲国产精品久久久_天天色天天色_亚洲人成一区_欧美一级欧美三级在线观看

CSS 實現3d輪播圖的一些思路,你學會了嗎?

開發 前端
原效果是通過vue的transition?組件實現的,感覺有些笨重,思考了一番,發現純 CSS也能實現這樣的效果,而且性能更好,實現也更簡潔,一起來看看吧!
最近在項目中碰到一個比較典型的3d輪播圖動效,如下所示:

圖片圖片

說難不難,說簡單也不簡單,這是一個無限循環的輪播效果,并且個數是固定的,你會如何實現呢?

原效果是通過vue的transition組件實現的,感覺有些笨重,思考了一番,發現純 CSS也能實現這樣的效果,而且性能更好,實現也更簡潔,一起來看看吧!

一、CSS 動畫實現思路

首先來分析一下思路。看著是一個連貫的輪播效果,其實單獨看每一個子項,都是完全相同的運動軌跡。

圖片圖片

然后是這個動畫,其實就是6個關鍵幀,逐一去位移和縮放,如下:

圖片圖片

然后給每個子項不同的“負延遲”,是不是就剛好錯開,形成一個完整的輪播效果了呢?

無論CSS怎么實現,動畫原理就這些了,下面來看幾個實現方式

二、CSS 動畫關鍵幀

首先簡單布局一下,先用一個元素實現動畫;

<div class="item"></div>

加點修飾;

html,body{
  font-family: -apple-system, "BlinkMacSystemFont", sans-serif;
  margin: 0;
  height: 100%;
  display: flex;
  justify-content: center;
  flex-direction: column;
  align-items: center;
  background: aliceblue;
  counter-reset: num;
}
.item{
  position: absolute;
  display: grid;
  place-content: center;
  width: 100px;
  height: 100px;
  border-radius: 8px;
  background-color: #3E65FF;
  color: #fff;
  font-size: 30px;
  counter-increment: num;
}

這里的數字是用CSS計數器生成的,效果如下:

圖片圖片

根據前面的關鍵幀,很容易用代碼實現,就是。

.item{
  animation: slide 12s infinite;
}
@keyframes slide {
  0%,100% {
    transform: translate(0%, 0%) scale(1);
  }
  16.67% {
    transform: translate(120%, -30%) scale(0.9);
  }
  33.33% {
    transform: translate(100%, -70%) scale(0.8);
  }
  50% {
    transform: translate(0, -90%) scale(0.7);
  }
  66.67% {
    transform: translate(-100%, -70%) scale(0.8);
  }
  83.33% {
    transform: translate(-120%, -30%) scale(0.9);
  }
}

這里的16.67%關鍵幀是將100%進行6等分得到的,如下所示:

圖片圖片

效果如下:

圖片圖片

雖然有動畫了,但是效果有點奇怪,每次改變位置的時候好像沒有停頓,顯得過渡有些緩慢,只是有減速和加速的過程,這是默認的ease-in-out的淡入淡出緩沖效果。

那么,如何拉開一定的間隔呢?也就是希望每次運動的快一點,然后停留一會。其實也很簡單,在之前的每個關鍵點前再添加一個相同的關鍵幀,比如在16.67%的前面一點6.67%,由于是相同的,所以這段時間內是沒有動畫的,也就相當于停留了一會。

圖片圖片

用代碼實現就是:

@keyframes slide {
  0%,90%,100% {
    transform: translate(0%, 0%) scale(1);
  }
  6.67%,
  16.67% {
    transform: translate(120%, -30%) scale(0.9);
  }
  23.33%,
  33.33% {
    transform: translate(100%, -70%) scale(0.8);
  }
  40%,
  50% {
    transform: translate(0, -90%) scale(0.7);
  }
  56.67%,
  66.67% {
    transform: translate(-100%, -70%) scale(0.8);
  }
  73.33%,
  83.33% {
    transform: translate(-120%, -30%) scale(0.9);
  }
}

這樣是不是就好多了?

圖片圖片

實現了一個,多個子元素也就好辦了。

<div class="item" style="--i: 0"></div>
<div class="item" style="--i: 1"></div>
<div class="item" style="--i: 2"></div>
<div class="item" style="--i: 3"></div>
<div class="item" style="--i: 4"></div>
<div class="item" style="--i: 5"></div>

我們給每個子元素加個CSS變量,然后給每個動畫加個“負延遲”,讓這個動畫提前運行到指定位置;

.item{
   animation: slide 12s calc(-2s * var(--i)) infinite;
}

效果如下:

基本就實現這個這個輪播動畫,不過層級還有點問題。

所以還需要再關鍵幀里加入層級變化;

@keyframes slide {
  0%,90%,100% {
    z-index: 4;
    transform: translate(0%, 0%) scale(1);
  }
  6.67%,
  16.67% {
    z-index: 3;
    transform: translate(120%, -30%) scale(0.9);
  }
  23.33%,
  33.33% {
    z-index: 2;
    transform: translate(100%, -70%) scale(0.8);
  }
  40%,
  50% {
    z-index: 1;
    transform: translate(0, -90%) scale(0.7);
  }
  56.67%,
  66.67% {
    z-index: 2;
    transform: translate(-100%, -70%) scale(0.8);
  }
  73.33%,
  83.33% {
    z-index: 3;
    transform: translate(-120%, -30%) scale(0.9);
  }
}

這樣就完美了。

這種實現兼容性最好,只用到了 CSS 動畫,兼容市面所有瀏覽器,可以放心使用

  • CSS 3d swiper (codepen.io)[1]
  • CSS 3d swiper (juejin.cn)[2]

三、CSS @property

其實目前來說,用上面這種方式就足夠了,沒有任何問題。

不過,上面對于中間停頓的處理方式可能有些繁瑣,下面再介紹另一種思路,可能更符合常規。

先思考一下,如果是用 JS要如何實現?是不是可以直接每隔2秒改變位移和縮放,然后通過transition實現過渡效果?

首先,我們還是需要像之前一樣,定義一些關鍵幀,不過不是直接改變位移和縮放,而是改變一些 CSS變量。

@keyframes slide {
  0%,100% {
    --translate: 0,0;
    --scale: 1;
    --z: 4;
  }
  16.67% {
    --translate: 120%,-30%;
    --scale: 0.9;
    --z: 3;
  }
  33.33% {
    --translate: 100%,-70%;
    --scale: 0.8;
    --z: 2;
  }
  50% {
    --translate: 0%,-90%;
    --scale: 0.7;
    --z: 1;
  }
  66.67% {
    --translate: -100%,-70%;
    --scale: 0.8;
    --z: 2;
  }
  83.33% {
    --translate: -120%,-30%;
    --scale: 0.9;
    --z: 3;
  }
}

然后每個子項就需要用transfrom來應用這些變量了;

.item{
  transform: translate(var(--translate)) scale(var(--scale));
  transition: .5s transform;
  animation: slide 12s calc(-2s * var(--i)) infinite;
}

我們來看看效果:

好像并沒有過渡動畫?這是因為animation覆蓋了transition,所以需要分離開來,我們嵌套一層父級。

<div class="item-wrap" style="--i: 0">
  <div class="item"></div>
</div>
<div class="item-wrap" style="--i: 1">
  <div class="item"></div>
</div>
<div class="item-wrap" style="--i: 2">
  <div class="item"></div>
</div>
<div class="item-wrap" style="--i: 3">
  <div class="item"></div>
</div>
<div class="item-wrap" style="--i: 4">
  <div class="item"></div>
</div>
<div class="item-wrap" style="--i: 5">
  <div class="item"></div>
</div>

然后將動畫寫在父級上;

.item-wrap{
  animation: slide 12s calc(-2s * var(--i)) infinite;
  display: contents;
}

這樣就不影響了,效果如下:

不過還是有點怪怪的。這是因為animation的默認效果也是ease-in-out,所以有這種漸入漸出的效果。我們需要瞬間變化,不需要過渡效果,因為過渡效果可以由transition完成。

這里我們可以用steps來實現,steps(1)表示直接切換,中間沒有任何過渡。

.item-wrap{
  animation: slide 12s calc(-2s * var(--i)) steps(1) infinite;
}

這樣效果就和前面基本一致了。

你也可以訪問以下鏈接來查看實際效果:

  • CSS 3d swiper @property (codepen.io)[3]
  • CSS 3d swiper @property (juejin.cn)[4]

雖然里面沒有提到CSS @property,但實際上是依賴這個特性的,因此兼容性稍差,需要Safari 16.4+,Firefox目前還不支持。

四、CSS 樣式查詢

拋開兼容性,其實還有一種方式可以實現,而且更容易理解,也更符合JS的思路。

我們要做的動畫很簡單,只需要改變一個 CSS變量就行,如下:

@property --index {
  syntax: "<number>";
  initial-value: 0;
  inherits: false;
}
@keyframes slide {
  0% {
    --index: 0;
  }
  100% {
    --index: 6;
  }
}

通過@property可以讓--index變量從0→6一次變化。

關于這個技巧,之前在多篇文章中都有提到。

你可能不需要 JS!CSS實現一個計時器。

如何讓CSS計數器支持小數的動態變化?

還在使用定時器嗎?CSS 也能實現電子時鐘。

動畫合成小技巧!CSS 實現動感的倒計時效果。

自定義計數器小技巧!CSS 實現長按點贊累積動畫。

實現如下:

.item-wrap{
  display: contents;
  animation: slide 12s calc(-2s * var(--i)) steps(6) infinite;
}

這樣就實現了一個--index不斷變化的動畫。

當然僅僅只是這樣還不夠,我們需要根據這個變量來匹配具體的樣式,這就要用到CSS樣式查詢了,具體實現如下:

@container style(--index: 0) {
  .item {
    transform: translate(0, 0) scale(1);
    z-index: 4;
  }
}
@container style(--index: 1) {
  .item {
    transform: translate(120%, -30%) scale(0.9);
    z-index: 3;
  }
}
@container style(--index: 2) {
  .item {
    transform: translate(100%, -70%) scale(0.8);
    z-index: 2;
  }
}
@container style(--index: 3) {
  .item {
    transform: translate(0, -90%) scale(0.7);
    z-index: 1;
  }
}
@container style(--index: 4) {
  .item {
    transform: translate(-100%, -70%) scale(0.8);
    z-index: 2;
  }
}
@container style(--index: 5) {
  .item {
    transform: translate(-120%, -30%) scale(0.9);
    z-index: 3;
  }
}

這段應該很好理解,比如@container style(--index: 5) 表示,當查詢到--index為5的時候,下面的樣式就生效了,非常像通過 JS 來改變類名一樣,這種方式也能實現類似的效果。

你也可以訪問以下鏈接來查看實際效果:

  • CSS 3d swiper @style (codepen.io)[5]
  • CSS 3d swiper @style (juejin.cn)[6]

由于要用到樣式查詢,所以兼容性更差一點,需要Chrome 111+,酌情使用。

五、總結一下

以上就是本文的全部內容了,共介紹了3種不同的實現思路,兼容性從高到低,大家可以自行選擇。

對了,還有一點,有時候我們需要鼠標hover時暫停動畫,這個就體現出CSS的優勢了,直接用:hover實現,類似這樣

.wrap:hover .item{
    animation-play-state: paused;
}

下面總結一下實現要點:

  1. 整體看著是一個連貫的輪播效果,其實單獨看每一個子項,都是完全相同的運動軌跡。
  2. 給每個子項不同的“負延遲”,就能形成一個完整的輪播效果。
  3. 動畫本質上是6個關鍵幀,只是位移和縮放的變化。
  4. 直接使用關鍵幀雖然有動畫,但是效果有點奇怪,每次改變位置的時候好像沒有停頓,顯得過渡有些緩慢。
  5. 可以手動在每個關鍵點前再添加一個相同的關鍵幀,手動停頓一下。
  6. 給每個子元素加個CSS變量,通過這個變量可以計算每個動畫的“負延遲”,讓這個動畫提前運行到指定。
  7. 我們還定義一些關鍵幀,不過不是直接改變位移和縮放,而是改變一些 CSS變量。
  8. 這樣可以實現每隔2秒改變位移和縮放,然后通過transition實現過渡效果。
  9. 這種思路依賴CSS @property,兼容性稍差,需要Safari 16.4+,Firefox目前還不支持。
  10. 還可以通過樣式查詢,自動匹配每種變量的位移和縮放,更符合常規思路,需要Chrome 111+
責任編輯:武曉燕 來源: 前端偵探
相關推薦

2022-07-08 09:27:48

CSSIFC模型

2022-05-06 09:00:56

CSS元素Flex

2022-10-09 09:30:33

CSS瀏覽器十六進制

2022-09-19 19:16:42

輪播圖has

2023-11-08 10:12:40

架構函數元素

2023-02-24 08:32:50

CSS漸變屬性

2022-06-16 07:50:35

數據結構鏈表

2022-10-27 09:13:58

CSSGradient

2023-12-07 12:29:49

Nginx負載均衡策略

2024-03-12 08:37:32

asyncawaitJavaScript

2024-07-29 10:35:44

KubernetesCSI存儲

2023-10-06 00:01:08

UML類圖圖形

2024-02-02 11:03:11

React數據Ref

2023-08-01 12:51:18

WebGPT機器學習模型

2024-01-02 12:05:26

Java并發編程

2024-01-19 08:25:38

死鎖Java通信

2024-02-04 00:00:00

Effect數據組件

2023-07-26 13:11:21

ChatGPT平臺工具

2023-01-10 08:43:15

定義DDD架構

2023-08-22 10:25:19

CSS動畫網頁
點贊
收藏

51CTO技術棧公眾號

主站蜘蛛池模板: 国产精品成人国产乱一区 | 视频一二三区 | 中文字幕 欧美 日韩 | 久久精品国产一区二区三区不卡 | 中文字幕一区在线观看视频 | 久久久久久国产精品免费免费 | 一区二区三区四区电影视频在线观看 | 午夜视频在线播放 | 国产一级毛片视频 | 国产精品久久久久久久久久久久久久 | 国产精品成人品 | 99re免费 | 天堂免费 | 一级片免费视频 | 成人精品系列 | 久久久久亚洲精品 | 国产区视频在线观看 | 欧美日韩国产三级 | 91精品国产自产精品男人的天堂 | 久久成人高清视频 | 国产成人99av超碰超爽 | 精品久久久久久久久久久久 | 久久综合久 | 日韩中出 | 超碰97av| 国产一级在线 | 日本三级网址 | 精品久久久一区二区 | 成人av色| 久久久久久久久久久久久九 | a视频在线播放 | 一区二区三区电影网 | 久久久免费 | 天天插天天射天天干 | 欧美一级三级在线观看 | 亚洲劲爆av | 亚洲视频免费 | 欧美成人精品在线 | 久热免费在线 | 欧美一级二级在线观看 | 国产午夜视频 |