首頁 >web前端 >css教學 >使用:has()關係偽類創建動畫,可點擊的卡

使用:has()關係偽類創建動畫,可點擊的卡

Christopher Nolan
Christopher Nolan原創
2025-03-10 12:21:13405瀏覽

Creating Animated, Clickable Cards With the :has() Relational Pseudo Class

Chrome和Safari瀏覽器已完全支持CSS的:has()偽類,該偽類正逐步在許多瀏覽器中推出。它通常被稱為“父選擇器”——我們可以通過子選擇器來選擇和設置父元素的樣式——但:has()的用途遠不止於此。其中一個用途是重新設計許多人經常使用的可點擊卡片模式。

我們將探討:has()如何幫助我們處理鏈接卡片,但首先……

:has()偽類是什麼?

已經有許多優秀的文章對:has()的用途進行了很好的解釋,但它仍然比較新,因此我們也應該在這裡簡單介紹一下。

:has()是一個關係偽類,它是W3C選擇器級別4工作草案的一部分。這就是括號的用途:匹配與特定子元素相關聯(更準確地說,是包含特定子元素)的元素。

<code>/* 匹配包含图像元素的article元素 */
article:has(img) { }

/* 匹配article元素,其内部直接包含图像 */
article:has(> img) { }</code>

因此,您可以理解為什麼我們可能將其稱為“父”選擇器。但是我們也可以將其與其他功能偽類結合使用以獲得更具體的匹配。假設我們想要設置樣式,使文章包含任何圖像。我們可以將:has()的關係能力與:not()的否定能力結合起來實現這一點:

<code>/* 匹配不包含图像的article元素 */
article:not(:has(img)) { }</code>

但這只是我們可以結合各種能力來使用:has()實現更多功能的開始。在我們專門解決可點擊卡片難題之前,讓我們看看目前在不使用:has()的情況下處理它們的一些方法。

我們目前如何處理可點擊卡片

如今,人們創建完全可點擊卡片主要有三種方法,為了充分理解這個偽類的強大功能,對其進行總結很有必要。

“鏈接作為包裝器”方法

這種方法經常使用。我從不使用這種方法,但我創建了一個快速演示來演示它:

這裡有很多問題,尤其是在可訪問性方面。當用戶使用旋轉器功能瀏覽您的網站時,他們會聽到該<a></a>元素內的完整文本——標題、文本和鏈接。有些人可能不想听完所有這些。我們可以做得更好。從HTML5開始,我們可以在<a></a>元素內嵌套塊元素。但這對我來說總感覺不對,尤其是因為這個原因。

優點:

  • 快速實現
  • 語義正確

缺點:

  • 可訪問性問題
  • 文本不可選擇
  • 覆蓋默認鏈接中使用的樣式非常麻煩

JavaScript方法

使用JavaScript,我們可以將鏈接附加到卡片,而不是將其寫入標記中。我找到了costdev的這個很棒的CodePen演示,它還在此過程中使卡片文本可選擇:

這種方法有很多好處。我們的鏈接在聚焦時是可訪問的,我們甚至可以選擇文本。但在樣式方面有一些缺點。例如,如果我們想為這些卡片添加動畫,我們必須在.card主包裝器而不是鏈接本身添加:hover樣式。當鏈接通過鍵盤製表鍵聚焦時,我們也不會從動畫中受益。

優點:

  • 可以實現完美的可訪問性
  • 可以選擇文本

缺點:

  • 需要JavaScript
  • 無法右鍵單擊(儘管可以通過一些額外的腳本修復)
  • 需要對卡片本身進行大量樣式設置,這在聚焦鏈接時不起作用

::after選擇器方法

此方法要求我們將卡片設置為相對定位,然後在鏈接的::after偽選擇器上設置絕對定位。這不需要任何JavaScript,並且很容易實現:

這裡有一些缺點,尤其是在選擇文本方面。除非您在卡片主體上提供更高的z-index,否則您將無法選擇文本,但如果您這樣做,請注意點擊文本不會激活您的鏈接。您是否想要可選擇文本取決於您。我認為這可能是一個用戶體驗問題,但這取決於用例。文本仍然可以通過屏幕閱讀器訪問,但我對這種方法的主要問題是缺乏動畫可能性。

優點:

  • 易於實現
  • 可訪問的鏈接,沒有冗余文本
  • 在懸停和聚焦時有效

缺點:

  • 文本不可選擇
  • 您只能為鏈接設置動畫,因為這是您懸停的元素。

一種新方法:將::after:has()結合使用

既然我們已經確定了可點擊卡片的現有方法,我想展示一下如何將:has()添加到混合中以解決大多數這些缺點。

事實上,讓我們將這種方法基於我們最後查看的使用鏈接元素上的::after的方法。我們實際上可以在那裡使用:has()來克服該方法的動畫限制。

讓我們從標記開始:

<code>/* 匹配包含图像元素的article元素 */
article:has(img) { }

/* 匹配article元素,其内部直接包含图像 */
article:has(> img) { }</code>

為了保持簡單,我將直接在CSS中定位元素,而不是使用類。

對於此演示,我們將為卡片添加圖像縮放和陰影以進行懸停,並為鏈接添加動畫,使箭頭彈出並更改鏈接的文本顏色。為了簡化操作,我們將為卡片添加一些作用域自定義屬性。這是基本的樣式:

<code>/* 匹配包含图像元素的article元素 */
article:has(img) { }

/* 匹配article元素,其内部直接包含图像 */
article:has(> img) { }</code>

很好!我們為圖像添加了初始縮放比例(--img-scale: 1.001)、卡片標題的初始顏色(--title-color: black)以及一些我們將用於使箭頭從鏈接中彈出的額外屬性。我們還設置了box-shadow聲明的空狀態,以便稍後對其進行動畫處理。這為我們現在需要創建的可點擊卡片設置了基礎,因此讓我們通過將這些自定義屬性添加到我們想要設置動畫的元素來添加一些重置和样式:

<code>/* 匹配不包含图像的article元素 */
article:not(:has(img)) { }</code>

讓我們對用戶友好一些,並在鏈接後面添加一個隱藏在屏幕閱讀器中的類:

<img src="/static/imghwm/default1.png" data-src="https://img.php.cn/" class="lazy" alt="Creating Animated, Clickable Cards With the :has() Relational Pseudo Class "><div clas="article-body">
    <h2>Some Heading</h2>
    <p>Curabitur convallis ac quam vitae laoreet. Nulla mauris ante, euismod sed lacus sit amet, congue bibendum eros. Etiam mattis lobortis porta. Vestibulum ultrices iaculis enim imperdiet egestas.</p>
    <a href="https://www.php.cn/link/93ac0c50dd620dc7b88e5fe05c70e15b">
      Read more
       <svg fill="currentColor" viewbox="0 0 20 20" xmlns="http://www.w3.org/2000/svg"><path clip-rule="evenodd" d="M12.293 5.293a1 1 0 011.414 0l4 4a1 1 0 010 1.414l-4 4a1 1 0 01-1.414-1.414L14.586 11H3a1 1 0 110-2h11.586l-2.293-2.293a1 1 0 010-1.414z" fill-rule="evenodd"></path></svg></a>
  </div>

我們的卡片開始看起來很漂亮了。是時候為它添加一些魔法了。使用:has()偽類,我們現在可以檢查我們的鏈接是否處於懸停或聚焦狀態,然後更新我們的自定義屬性並添加box-shadow。使用這少量CSS代碼,我們的卡片真正栩栩如生:

/* 卡片元素 */
article {
  --img-scale: 1.001;
  --title-color: black;
  --link-icon-translate: -20px;
  --link-icon-opacity: 0;

  position: relative;
  border-radius: 16px;
  box-shadow: none;
  background: https://www.php.cn/link/93ac0c50dd620dc7b88e5fe05c70e15bfff;
  transform-origin: center;
  transition: all 0.4s ease-in-out;
  overflow: hidden;
}
/* 链接的::after伪元素 */
article a::after {
  content: "";
  position: absolute;
  inset-block: 0;
  inset-inline: 0;
  cursor: pointer;
}

看到上面的內容了嗎?現在,如果卡片中的任何子元素處於懸停或聚焦狀態,我們都會獲得更新的樣式。即使鏈接元素是唯一可以在::after可點擊卡片方法中包含懸停或聚焦狀態的元素,我們也可以使用它來匹配父元素並應用轉換。

就是這樣。 :has()選擇器的另一個強大的用例。我們不僅可以通過聲明其他元素作為參數來匹配父元素,還可以使用偽類來匹配和設置父元素的樣式。

優點:

  • 可訪問的
  • 可設置動畫
  • 不需要JavaScript
  • 在正確的元素上使用:hover

缺點:

  • 文本不容易選擇。
  • 瀏覽器支持僅限於Chrome和Safari(在Firefox中,它在標誌後面受支持)。

這是一個使用此技術的演示。您可能會注意到卡片周圍有一個額外的包裝器,但這只是我在使用容器查詢時進行的一些嘗試,這只是所有主要瀏覽器中正在推出的其他一些很棒的功能之一。

您是否有一些其他示例想要分享?評論部分非常歡迎其他解決方案或想法。

以上是使用:has()關係偽類創建動畫,可點擊的卡的詳細內容。更多資訊請關注PHP中文網其他相關文章!

陳述:
本文內容由網友自願投稿,版權歸原作者所有。本站不承擔相應的法律責任。如發現涉嫌抄襲或侵權的內容,請聯絡admin@php.cn
上一篇:現在有太多CSS嗎?下一篇:暫無