CSS3偽類和偽元素的特性和區別

来源:http://www.cnblogs.com/floor/archive/2017/04/01/6657806.html
-Advertisement-
Play Games

今天複習css時發現::的css選擇器,查了一下,知道有偽元素和偽類這件事,他們的區別是什麼呢?很幸運已經有人總結好了!CSS3偽類和偽元素的特性和區別。前端er們大都或多或少地接觸過CSS偽類和偽元素,比如最常見的:focus,:hover以及標簽的:link、visited等,偽元素較常見的比如... ...


本文轉自:http://www.cnblogs.com/ihardcoder/p/5294927.html

今天複習css時發現::的css選擇器,查了一下,知道有偽元素和偽類這件事,他們的區別是什麼呢?很幸運已經有人總結好了!

CSS3偽類和偽元素的特性和區別

前端er們大都或多或少地接觸過CSS偽類和偽元素,比如最常見的:focus,:hover以及<a>標簽的:linkvisited等,偽元素較常見的比如:before:after等。

其實上面提到的這些偽類和偽元素都是CSS1和CSS2中的概念,CSS1和CSS2中對偽類的偽元素的區別比較模糊,甚至經常有同行將:before:after稱為偽類。CSS3對這兩個概念做了相對較清晰地概念,並且在語法上也很明顯的講二者區別開。

偽類 - pseudo classes

首先看看CSS2中對偽類的定義:

CSS 偽類用於向某些選擇器添加特殊的效果

單單看定義完全不懂在講什麼。截止CSS2,偽類有以下幾種(偷個懶,截圖引自W3School):

然後是CSS3對偽類的定義:

The pseudo-class concept is introduced to permit selection based on information that lies outside of the document tree or that cannot be expressed using the other simple selectors.

A pseudo-class always consists of a "colon" (:) followed by the name of the pseudo-class and optionally by a value between parentheses.

Pseudo-classes are allowed in all sequences of simple selectors contained in a selector. Pseudo-classes are allowed anywhere in sequences of simple selectors, after the leading type selector or universal selector (possibly omitted). Pseudo-class names are case-insensitive. Some pseudo-classes are mutually exclusive, while others can be applied simultaneously to the same element. Pseudo-classes may be dynamic, in the sense that an element may acquire or lose a pseudo-class while a user interacts with the document.

簡單翻譯一下:

偽類存在的意義是為了通過選擇器找到那些不存在與DOM樹中的信息以及不能被常規CSS選擇器獲取到的信息。

偽類由一個冒號:開頭,冒號後面是偽類的名稱和包含在圓括弧中的可選參數。

任何常規選擇器可以再任何位置使用偽類。偽類語法不區別大小寫。一些偽類的作用會互斥,另外一些偽類可以同時被同一個元素使用。並且,為了滿足用戶在操作DOM時產生的DOM結構改變,偽類也可以是動態的。

其實第一段話就囊括CSS3偽類的全部定義了,這段話中指出CSS3偽類的功能有兩種:

  1. 獲取不存在與DOM樹中的信息。比如<a>標簽的:linkvisited等,這些信息不存在與DOM樹結構中,只能通過CSS選擇器來獲取;
  2. 獲取不能被常規CSS選擇器獲取的信息。比如偽類:target,它的作用是匹配文檔(頁面)的URI中某個標誌符的目標元素,例如我們可以通過如下代碼來實現頁面內的區域跳轉:
<ul class="tabs">
    <li><a href="#tab1">標簽一</a></li>
    <li><a href="#tab2">標簽二</a></li>
    <li><a href="#tab3">標簽三</a></li>
</ul>
<div id="tab1" class="tab_content">
<!--tabed content--></div>
<div id="tab2" class="tab_content">
<!--tabed content--></div>
<div id="tab3" class="tab_content">
<!--tabed content--></div>

CSS代碼如下:

.tab_content {
  height: 800px;
  background: red;
  margin-bottom: 100px;
}
#tab1:target, #tab2:target, #tab3:target {
    background:blue;
}

當然,通過JavaScript來獲取window.location.hash同樣可以實現上例中的效果,但這是另外一回事了。總之,:target通過CSS實現了常規CSS無法實現的邏輯

其實對比來看,CSS2中對偽類的定義也是合理地,但是它並未指出“某些選擇器”是“哪些選擇器”,CSS3對偽類的定義就顯得明確了很多。

再舉個慄子,通過:nth-child()偽類可以實現一些很有意思的效果,比如:

table tr:nth-child(2n) td{
   background-color: #ccc;
}
table tr:nth-child(2n+1) td{
   background-color: #fff;
}
table tr:nth-child(2n+1):nth-child(5n) td{
   background-color: #f0f;
}

上面的代碼將所有偶數行背景色設置為#ccc,不能被5整除的奇數行設置背景色#fff,能夠被5整除的奇數行設置背景色#f0f

如果不使用偽類而是使用JavaScript代碼來實現上述的效果,恐怕要複雜很多。

可以總結出:nth-child()偽類的效果是將被常規css選擇器篩選出的元素按照既定規定進行再次篩選。

CSS3中還引入了許多新的偽類,感興趣的讀者可以參考這裡

偽元素 - Pseudo-elements

CSS2中對偽元素的定義:

CSS 偽元素用於向某些選擇器設置特殊效果

好吧,跟偽類的定義完全一樣有木有(吐槽一下W3School的翻譯)。其實人家這樣翻譯也沒有錯,本來CSS2對偽類和偽元素的定義就是完全一樣的:

CSS introduces the concepts of pseudo-elements and pseudo-classes to permit formatting based on information that lies outside the document tree.

截止CSS2,偽元素有以下幾種:

然後再看CSS3中偽元素的定義

Pseudo-elements create abstractions about the document tree beyond those specified by the document language. For instance, document languages do not offer mechanisms to access the first letter or first line of an element's content. Pseudo-elements allow authors to refer to this otherwise inaccessible information. Pseudo-elements may also provide authors a way to refer to content that does not exist in the source document (e.g., the ::before and ::after pseudo-elements give access to generated content).

A pseudo-element is made of two colons (::) followed by the name of the pseudo-element.

This :: notation is introduced by the current document in order to establish a discrimination between pseudo-classes and pseudo-elements. For compatibility with existing style sheets, user agents must also accept the previous one-colon notation for pseudo-elements introduced in CSS levels 1 and 2 (namely, :first-line, :first-letter, :before and :after). This compatibility is not allowed for the new pseudo-elements introduced in this specification.

Only one pseudo-element may appear per selector, and if present it must appear after the sequence of simple selectors that represents the subjects of the selector.

Note: A future version of this specification may allow multiple pseudo-elements per selector.

簡單翻譯一下:

偽元素在DOM樹中創建了一些抽象元素,這些抽象元素是不存在於文檔語言里的(可以理解為html源碼)。比如:documen介面不提供訪問元素內容的第一個字或者第一行的機制,而偽元素可以使開發者可以提取到這些信息。並且,一些偽元素可以使開發者獲取到不存在於源文檔中的內容(比如常見的::before,::after)。

偽元素的由兩個冒號::開頭,然後是偽元素的名稱。

使用兩個冒號::是為了區別偽類和偽元素(CSS2中並沒有區別)。當然,考慮到相容性,CSS2中已存的偽元素仍然可以使用一個冒號:的語法,但是CSS3中新增的偽元素必須使用兩個冒號::

一個選擇器只能使用一個偽元素,並且偽元素必須處於選擇器語句的最後。

註:不排除未來會加入同時使用多個偽元素的機制。

同樣,第一段話是偽元素的清晰定義,也是偽元素與偽類最大的區別。簡單來說,偽元素創建了一個虛擬容器,這個容器不包含任何DOM元素,但是可以包含內容。另外,開發者還可以為偽元素定製樣式。

::first-line為例,它獲取了指定元素的第一行內容並且將第一行的內容加入到虛擬容器中。如果通過JavaScript來實現這個邏輯,那麼要考慮的因素就太多了,比如制定元素的寬度、字體大小,甚至浮動元素的圖文混排等等。當然,這些問題確實是可以用JavaScript來解決的,但是相對於::first-line簡簡單單的幾個字,用JavaScript恐怕不止這些吧!

舉個綜合使用偽類和偽元素的慄子:

q:lang(de)::after{
    content: " (German) ";
}
q:lang(en)::after{
    content: " (English) ";
}
q:lang(fr)::after{
    content: " (French) ";
}
q:not(:lang(fr)):not(:lang(de)):not(:lang(en))::after{
    content: " (Unrecognized language) ";
}

以上代碼通過偽類"lang獲取不同lang屬性的節點,併為之設置偽元素::after,偽元素的內容是此節點的語言類型。

最後,總結一下偽類與偽元素的特性及其區別:

  1. 偽類本質上是為了彌補常規CSS選擇器的不足,以便獲取到更多信息;
  2. 偽元素本質上是創建了一個有內容的虛擬容器;
  3. CSS3中偽類和偽元素的語法不同;
  4. 可以同時使用多個偽類,而只能同時使用一個偽元素;

您的分享是我們最大的動力!

-Advertisement-
Play Games
更多相關文章
  • 慕課網的一個小課程,練習了一遍,不足之處,歡迎指正(照片在本地,大家可以著重看代碼哈): 下麵再看下JS代碼實現: ...
  • 瀏覽器緩存,也就是客戶端緩存,既是網頁性能優化裡面靜態資源相關優化的一大利器,也是無數web開發人員在工作過程不可避免的一大問題。瀏覽器緩存分為:強緩存和協商緩存 (1)原理: 1.瀏覽器載入資源時,先根據這個資源的http header中的Cache-Control判斷是否命中強緩存,如果命中,瀏 ...
  • 1.頁面載入時向body載入文本、彈出框 <body> <script> document.write("<h1>JavaScript 會在頁面載入時向 HTML 的 <body> 寫文本</h1>"); </script> <script> alert("載入頁面彈出框"); </script>< ...
  • 在很多時候都需要用到驗證碼,前端驗證碼需要知道Html5中的canvas知識點。驗證碼生成步驟是:1.生成一張畫布canvas 2.生成隨機數驗證碼 3.在畫布中生成干擾線 4.把驗證碼文本填充到畫布中 5.點擊畫布更換驗證碼 結構與樣式: 下麵來編寫js代碼: 這樣就寫好一個較普通的驗證碼了,當然 ...
  • 原文標題:UI5 Programming Examples 本文鏈接:http://www.cnblogs.com/hhelibeb/p/6654829.html 大家好, 首先,我想對貢獻了這些例子的人們說句謝謝。 1. 表示例: 獲取選定行的值 JS Bin – Collaborative Ja ...
  • 複習CSS時發現很多選擇器不會,因為平時很少用到。現在乾脆一不做二不修,全部溫習一遍。本文參考http://css.doyoe.com/. ...
  • 總結了三種非同步請求方式,XHR、Promise和Fetch,以及兩種跨域方案JSONP和CORS。文章淺顯移動,圖片豐富。不信?你進來看啊。 ...
  • 1.onclick事件 <button type="button" onclick="alert('Welcome!')">點擊這裡</button> <div onclick="alert('Welcome!')">點擊這個div</div> 2.改變 HTML 內容 添加按鈕,並調用onclic ...
一周排行
    -Advertisement-
    Play Games
  • 移動開發(一):使用.NET MAUI開發第一個安卓APP 對於工作多年的C#程式員來說,近來想嘗試開發一款安卓APP,考慮了很久最終選擇使用.NET MAUI這個微軟官方的框架來嘗試體驗開發安卓APP,畢竟是使用Visual Studio開發工具,使用起來也比較的順手,結合微軟官方的教程進行了安卓 ...
  • 前言 QuestPDF 是一個開源 .NET 庫,用於生成 PDF 文檔。使用了C# Fluent API方式可簡化開發、減少錯誤並提高工作效率。利用它可以輕鬆生成 PDF 報告、發票、導出文件等。 項目介紹 QuestPDF 是一個革命性的開源 .NET 庫,它徹底改變了我們生成 PDF 文檔的方 ...
  • 項目地址 項目後端地址: https://github.com/ZyPLJ/ZYTteeHole 項目前端頁面地址: ZyPLJ/TreeHoleVue (github.com) https://github.com/ZyPLJ/TreeHoleVue 目前項目測試訪問地址: http://tree ...
  • 話不多說,直接開乾 一.下載 1.官方鏈接下載: https://www.microsoft.com/zh-cn/sql-server/sql-server-downloads 2.在下載目錄中找到下麵這個小的安裝包 SQL2022-SSEI-Dev.exe,運行開始下載SQL server; 二. ...
  • 前言 隨著物聯網(IoT)技術的迅猛發展,MQTT(消息隊列遙測傳輸)協議憑藉其輕量級和高效性,已成為眾多物聯網應用的首選通信標準。 MQTTnet 作為一個高性能的 .NET 開源庫,為 .NET 平臺上的 MQTT 客戶端與伺服器開發提供了強大的支持。 本文將全面介紹 MQTTnet 的核心功能 ...
  • Serilog支持多種接收器用於日誌存儲,增強器用於添加屬性,LogContext管理動態屬性,支持多種輸出格式包括純文本、JSON及ExpressionTemplate。還提供了自定義格式化選項,適用於不同需求。 ...
  • 目錄簡介獲取 HTML 文檔解析 HTML 文檔測試參考文章 簡介 動態內容網站使用 JavaScript 腳本動態檢索和渲染數據,爬取信息時需要模擬瀏覽器行為,否則獲取到的源碼基本是空的。 本文使用的爬取步驟如下: 使用 Selenium 獲取渲染後的 HTML 文檔 使用 HtmlAgility ...
  • 1.前言 什麼是熱更新 游戲或者軟體更新時,無需重新下載客戶端進行安裝,而是在應用程式啟動的情況下,在內部進行資源或者代碼更新 Unity目前常用熱更新解決方案 HybridCLR,Xlua,ILRuntime等 Unity目前常用資源管理解決方案 AssetBundles,Addressable, ...
  • 本文章主要是在C# ASP.NET Core Web API框架實現向手機發送驗證碼簡訊功能。這裡我選擇是一個互億無線簡訊驗證碼平臺,其實像阿裡雲,騰訊雲上面也可以。 首先我們先去 互億無線 https://www.ihuyi.com/api/sms.html 去註冊一個賬號 註冊完成賬號後,它會送 ...
  • 通過以下方式可以高效,並保證數據同步的可靠性 1.API設計 使用RESTful設計,確保API端點明確,並使用適當的HTTP方法(如POST用於創建,PUT用於更新)。 設計清晰的請求和響應模型,以確保客戶端能夠理解預期格式。 2.數據驗證 在伺服器端進行嚴格的數據驗證,確保接收到的數據符合預期格 ...