国产精品电影_久久视频免费_欧美日韩国产激情_成年人视频免费在线播放_日本久久亚洲电影_久久都是精品_66av99_九色精品美女在线_蜜臀a∨国产成人精品_冲田杏梨av在线_欧美精品在线一区二区三区_麻豆mv在线看

借助 :has 實現3D輪播圖

開發 前端
這次借助:has來實現這樣的功能,相信可以帶來不一樣的思路,一起看看吧!

這次帶來一個比較常見的案例,3d 輪播圖,就像這樣的:

圖片

這個輪播圖有幾個需要實現的點:

  1. 3d 視覺,也就是中間大,兩邊小。
  2. 自動輪播,鼠標放上自動暫停。
  3. 點擊任意卡片會立即跳轉到該卡片。

這次借助:has來實現這樣的功能,相信可以帶來不一樣的思路,一起看看吧!

溫馨提醒:兼容性要求需要 Chrome 101+,并且開始實驗特性(105+正式支持),Safari 15.4+,Firefox 官方說開啟實驗特性可以支持,但是實測并不支持。

一、3d 視覺樣式

這一部分才是重點。

首先我們來簡單布局一下,假設HTML是這樣的:

<div class="view" id="view">
<div class="item">1</div>
<div class="item">2</div>
<div class="item">3</div>
<div class="item">4</div>
<div class="item current">5</div>
<div class="item">6</div>
<div class="item">7</div>
<div class="item">8</div>
<div class="item">9</div>
<div class="item">10</div>
</div>

為了盡可能減少復雜度,我們可以將所有的變化都集中在一個類名上。

比如.current?表示當前選中項,也就是中間的那項。這里采用絕對定位的方式,將所有卡片項都堆疊在一起,然后設置3d?視圖,將卡片的Z?軸往后移動一段距離,讓.current在所有卡片的最前面,實現近大遠小的效果,具體實現如下:

.view {
position: relative;
width: 400px;
height: 250px;
transform-style: preserve-3d;
perspective: 500px;
}
.item {
position: absolute;
width: 100%;
height: 100%;
border-radius: 8px;
display: grid;
place-content: center;
box-shadow: 2px 2px 10px rgba(0, 0, 0, 0.1);
transform: translate3d(0, 0, -100px);
}
.item.current {
transform: translate3d(0, 0, 0);
}

效果如下:

圖片

其實層級是這樣的,可以在 Chrome 圖層中看到:

圖片

現在,我們需要讓相鄰左右兩邊的都漏出來,右邊的比較容易,用相鄰兄弟選擇器??+??就可以了

.item.current + .item{
transform: translate3d(30%, 0, -100px);
}

那相鄰左邊的呢?以前是無解的,只能通過 JS 分別設置不同的類名,非常麻煩,但現在有了??:has??偽類,也可以輕松實現了,如下

.item:has(+.item.current){
transform: translate3d(-30%, 0, -100px);
}

效果如下:

圖片

不過還有一些臨界情況,比如在第一個卡片時,由于前面沒有兄弟節點了,所以就成了這樣。

圖片

所以需要再在第一個元素時,把最后一個元素放在它的左邊,第一個元素是:first-child?,最后一個元素是:last-child,所以實現是這樣的(最后一個元素處理同理)。

.item.current:first-child ~ .item:last-child {
transform: translate3d(-30%, 0, -100px);
opacity: 1;
}
.item:first-child:has(~ .item.current:last-child) {
transform: translate3d(30%, 0, -100px);
opacity: 1;
}

這樣就處理好了邊界情況。

圖片

進一步,還可以向兩側露出兩個卡片,實現也是類似的,完整實現如下:

/*當前項*/
.item.current {
transform: translate3d(0, 0, 0);
}
/*當前項右1*/
.item.current + .item,
.item:first-child:has(~ .item.current:last-child) {
transform: translate3d(30%, 0, -100px);
}
/*當前項左1*/
.item:has(+ .item.current),
.item.current:first-child ~ .item:last-child {
transform: translate3d(-30%, 0, -100px);
}
/*當前項右2*/
.item.current + .item + .item,
.item:first-child:has(~ .item.current:nth-last-child(2)),
.item:nth-child(2):has(~ .item.current:last-child) {
transform: translate3d(50%, 0, -150px);
}
/*當前項左2*/
.item:has(+.item + .item.current),
.item.current:first-child ~ .item:nth-last-child(2),
.item.current:nth-child(2) ~ .item:last-child{
transform: translate3d(-50%, 0, -150px);
}

這樣就實現了關于.current的全部樣式處理了,只用一個變量就控制了所有變化。

圖片

二、自動輪播和暫停

有了上面的處理,接下來的邏輯就非常簡單了,只需要通過js動態控制.current的變化就行了。

一般情況下,我們可能會想到用定時器setInterval,但這里,我們也可以不使用定時器,借助 CSS 動畫的力量,可以更輕松地完整這樣的交互。

要做的事情很簡單,給容器添加一個無關緊要的 CSS 動畫。

.view {
/**/
animation: scroll 3s infinite;
}
@keyframes scroll {
to {
transform: translateZ(.1px); /*無關緊要的動畫樣式*/
}
}

這樣就得到了一個時長為3s,無限循環的動畫了。

然后,監聽animationiteration?事件,這個事件在動畫每次運行一次就會回調一次,在這里也就是每3s?運行一次,就像setInterval的功能一樣

GlobalEventHandlers.onanimationiteration - Web API 接口參考 | MDN (mozilla.org)[1]。

在animationiteration?回調中處理.current?邏輯,很簡單,移除當前的.current?,給下一個添加.current,注意一下邊界就行了,具體實現如下:

view.addEventListener("animationiteration", () => {
const current = view.querySelector(".current") || view.firstElementChild;
current.classList.remove("current");
if (current.nextElementSibling) {
current.nextElementSibling.classList.add("current");
} else {
view.firstElementChild.classList.add("current");
}
});

使用animationiteration的最大好處是,可以直接通過 CSS 進行動畫的控制,再也無需監聽鼠標移入移出事件了。

.view:hover{
animation-play-state: paused;
}

效果如下(方便演示,速度調快了)。

圖片

三、點擊快速切換

點擊切換,我其實最先想到的是通過:checked,也就是類似單選,比如:

<div class="view" id="view">
<label class="item"><input type="radio" checked name="item"></label>
<label class="item"><input type="radio" name="item"></label>
<label class="item"><input type="radio" name="item"></label>
<label class="item"><input type="radio" name="item"></label>
<label class="item"><input type="radio" name="item"></label>
<label class="item"><input type="radio" name="item"></label>
</div>

但是目前來看??:has??偽類貌似不支持多層嵌套,比如下面這條語句。

.item:has(+.item:has(:checked)){
/*不生效*/
}

.item:has(:checked)選中的是子元素被選中的父級,然后.item:has(+.item:has(:checked))表示選中它的前面一個兄弟節點,這樣就能實現選中功能了,可惜現在并不支持??(以后可能支持)。

沒辦法,只能通過傳統方式來實現,直接綁定監聽click事件。

view.addEventListener("click", (ev) => {
const current = view.querySelector(".current") || view.firstElementChild;
current.classList.remove("current");
ev.target.closest('.item').classList.add("current");
});

效果如下:

圖片

完整代碼可以查看線上 demo:CSS 3d scroll (codepen.io)[2]或者CSS 3dscroll(runjs.work)[3]。

四、總結一下

以上就是借助:has偽類來實現一個3d輪播圖的全部細節了,所有的視覺變化全部在 CSS 中完成,JS 只需要處理切換邏輯就行了,相比以前而言,實現上更加簡潔和優雅,下面總結一下。

  1. 3d 視覺樣式可以通過transform-style: preserve-3d;實現近大遠小的效果。
  2. 通過.item:has(+.item.current)可以設置當前項前面的兄弟節點。
  3. 還需要考慮第一個和最后一個這兩種臨界情況。
  4. 輪播圖自動輪播和暫停可以借助animationiteration?回調,這種方式的優勢是可以通過:hover控制。
  5. :has偽類貌似不支持多層嵌套,希望以后可以支持吧~

:has非常強大,目前唯一的缺陷在于兼容性。好在瀏覽器對于這一新特性跟進的都比較積極,明年這個時候差不多可以在內部項目用起來了。

參考資料

?[1]GlobalEventHandlers.onanimationiteration - Web API 接口參考 | MDN (mozilla.org): https://developer.mozilla.org/zh-CN/docs/Web/API/Element/animationiteration_event。

[2]CSS 3d scroll (codepen.io): https://codepen.io/xboxyan/pen/PoeGjdg。

[3]CSS 3dscroll(runjs.work): https://runjs.work/projects/6a42a4c284e4442c。?

責任編輯:姜華 來源: 前端偵探
相關推薦

2024-07-03 10:36:14

2011-09-22 10:07:52

奧圖碼投影儀

2011-12-21 12:46:43

2012-06-16 16:57:52

WebGL

2012-02-27 10:00:50

HTML 5

2024-12-23 15:46:59

2011-05-26 10:55:39

2024-07-16 12:02:11

2013-07-23 07:03:51

Android開發學習Gallery實現3DAndroid源碼下載

2014-09-12 10:30:51

HTML5熱力圖

2021-09-16 07:52:18

SwiftUScroll效果

2011-10-06 13:30:45

宏碁投影儀

2016-12-01 09:24:56

Android

2024-03-20 15:51:00

AI數據

2012-11-26 12:51:44

木材3D打

2023-05-26 07:08:05

CSS模糊實現文字

2010-06-09 10:50:08

OpenSUSE 3D

2024-12-10 15:17:11

2009-04-02 13:44:59

linuxOpenSUSE安裝界面

2011-08-22 14:28:48

奧圖碼投影機
點贊
收藏

51CTO技術棧公眾號

国产福利图片| 亚洲人一区二区| 超碰在线最新网址| 国产精品伦理在线| 国产精品三级网站| 高潮久久久久久久久久久久久久| 一本到不卡精品视频在线观看| 男女视频网站在线观看| 久久免费精品视频在这里| 欧美激情网站在线观看| 欧美电影网站| 国产丝袜一区二区三区| 一本一道波多野毛片中文在线| 亚洲自拍偷拍网站| 美女露隐私免费网站| 亚洲欧洲成人自拍| 国产剧情演绎av| 3p在线观看| 久久天堂av综合合色蜜桃网| 亚洲日本在线看| 国产一二三四五| 日韩视频免费直播| 日韩欧美在线番号| 天美av一区二区三区久久| 日韩激情片免费| 国产一区二区高清在线| 在线精品视频一区二区三四| 色综合久久久久久久久五月| 午夜一级久久| 免费成人在线视频网站| 久久一区精品| 1024精品视频| 色婷婷综合久久久中文一区二区| 高清av在线| 成人免费黄色网| 国产丝袜一区| 97视频在线观看免费| 久久国产综合精品| 日韩欧美三级一区二区| 国产日韩欧美不卡| 欧美国产一区二区| 欧美色老女人| 性感美女极品91精品| 免费资源在线观看| 精品欧美久久久| 成人国产精品入口免费视频| 久久在线观看视频| av中字幕久久| 麻豆精品视频| av在线不卡免费看| 啊灬啊灬啊灬啊灬高潮在线看| 一本色道久久综合亚洲aⅴ蜜桃| 免费网站成人| 亚洲视屏在线播放| 红杏aⅴ成人免费视频| 91久久精品美女| 蜜臀精品一区二区三区在线观看| 精品国偷自产一区二区三区| 欧产日产国产精品视频 | 国产一区不卡| 免费97视频在线精品国自产拍| 日韩免费高清视频网站| 久久精品精品电影网| 3atv一区二区三区| 成人观看网址| 26uuu另类亚洲欧美日本老年| 日韩在线二区| 色一情一乱一伦一区二区三欧美 | 麻豆传媒在线视频| 欧美日韩在线一区二区| аⅴ资源天堂资源库在线| 午夜精品久久久久久久99热| 欧美艹逼视频| 欧美在线视频播放| 91麻豆国产香蕉久久精品| 69精品丰满人妻无码视频a片| 黄色免费在线看| 色777狠狠综合秋免鲁丝| 天海翼一区二区三区四区在线观看| 在线成人午夜影院| 欧美男男freegayvideosroom| 久久久久高清| 亚洲精品国产成人久久av盗摄| 新版中文在线官网| 4388成人网| 先锋av资源在线| 国产亚洲欧洲高清| 国产精品一区二区无线| 三上悠亚在线观看二区| 色老头久久综合| 日本一区二区成人在线| julia中文字幕久久亚洲蜜臀| 欧美成人午夜| 综合操久久久| 在线观看av一区二区| jizzjizzjizz欧美| 中文精品一区二区三区| 一区二区三区日韩欧美精品| 国产美女情趣调教h一区二区| 国产精品99久久久久久久久久久久| 国产精品一二三| 伊人福利在线| 成人av资源网| 亚洲福利一二三区| 99精品国产高清一区二区麻豆| 男同互操gay射视频在线看| 欧美性大战久久久久久久蜜臀 | 国产精品日韩一区二区| 国产精品电影院| 91精品麻豆| 欧美人与动牲交xxxxbbbb| 91麻豆精品国产91久久久| 99精品一区| av黄色免费| 国产91精品视频在线观看| 久久先锋影音av鲁色资源网| 色8久久影院午夜场| 欧美在线日韩精品| 欧美性生活一区| 综合久久久久| 国产永久免费高清在线观看| 国产免费成人av| 亚洲亚洲精品在线观看| 国产精品免费大片| 爱爱永久免费视频| 欧美一区三区三区高中清蜜桃| 久久女同性恋中文字幕| 精品中文字幕一区二区三区| 99精品人妻少妇一区二区| 日韩在线视频二区| 99久久精品国产一区| 99久久999| 毛葺葺老太做受视频| 欧美精品videosex牲欧美| 国产精品情趣视频| 九九综合久久| 超碰在线免费| 91久久精品www人人做人人爽| 欧美天天综合色影久久精品| 亚洲精品一区二区妖精| 成人高潮成人免费观看| 日本不卡一区二区三区视频| 亚洲精品在线三区| 国产一区二区精品久久| av在线精品| 国产午夜视频| 春色成人在线视频| 日韩欧美中文一区| 国产一区二区调教| 国产一区二区不卡视频| 欧美在线看片a免费观看| 日韩视频久久| 亚洲大胆人体大胆做受1| 妞干网这里只有精品| 精品国内自产拍在线观看| 国产精品国产a| 欧美成人首页| 成人短视频在线观看| 玖玖精品在线视频| 久久777国产线看观看精品| 一区二区三区成人在线视频| 欧美xxx在线观看| 丁香花在线高清完整版视频| 乱熟女高潮一区二区在线| 韩国国内大量揄拍精品视频| 天天综合网天天综合色| 国产日韩精品入口| 亚洲一卡二卡三卡四卡无卡网站在线看 | 成人做爰视频www网站小优视频| 青娱乐一区二区| 99久久免费国产| av综合网站| 国内精品久久久久久久果冻传媒| 日本三级在线播放完整版| 欧美另类老女人| 欧美不卡123| 天堂av在线网| 国产欧美日韩另类视频免费观看| www99热| 日韩在线中文字| 久久伊人精品| 在线观看欧美| 国产高清免费在线| 亚洲国产精品www| 91福利在线播放| 国产精品国产自产拍高清av水多| 国产精品一区二区三| 欧美激情一区二区三区成人| 久久国产视频网站| 最新69国产成人精品视频免费| 九九99玖玖| 成人毛片100部免费看| 美女在线免费视频| 一区二区在线播放视频| 成人免费观看在线网址| 国产天堂av| 国产大学生校花援交在线播放| 菠萝菠萝蜜在线观看| 少妇人妻在线视频| 国产ts人妖一区二区三区|