<kbd id="afajh"><form id="afajh"></form></kbd>
<strong id="afajh"><dl id="afajh"></dl></strong>
    <del id="afajh"><form id="afajh"></form></del>
        1. <th id="afajh"><progress id="afajh"></progress></th>
          <b id="afajh"><abbr id="afajh"></abbr></b>
          <th id="afajh"><progress id="afajh"></progress></th>

          關(guān)于 z-index,你可能一直存在誤區(qū)

          共 5456字,需瀏覽 11分鐘

           ·

          2021-01-29 10:53

          • 原文地址:What You May Not Know About the Z-Index Property
          • 原文作者:Steven Bradley
          • 譯者:Chor

          z-index 這個屬性表面看上去很簡單,但如果你想搞清楚其工作原理的話,其實(shí)是有不少值得探討之處的。本文將從層疊上下文(stacking contexts)和一些實(shí)際案例出發(fā),談一談 z-index 的內(nèi)部工作原理。

          CSS 為盒模型的布局提供了三種不同的定位方案[1]

          • 正常文檔流
          • 浮動
          • 定位

          最后一種方案(特指絕對定位)將會把元素從正常文檔流中完全移走,其最終的落腳點(diǎn)將取決于開發(fā)者。

          通過設(shè)置 topleftbottomright 的值,你可以在二維空間中對元素進(jìn)行定位,但 CSS 同時也允許你使用 z-index 屬性[2] 把它放置在三維空間中。

          表面看起來,z-index 似乎是一個很簡單的屬性,你給它設(shè)置哪個值,元素就會位于 y 軸的哪個位置,就這樣。但它實(shí)際上并沒有我們想象的這么簡單,這個屬性背后是一系列決定元素所在層級的規(guī)則。

          為了保證我們在同一個“頻道”上,這里我先普及一些基礎(chǔ)概念,之后再解釋層疊的相關(guān)知識,并在一些場景中體會 ?z-index[3] 作用的機(jī)制。

          Z-Index 的基礎(chǔ)概念

          對于三維空間坐標(biāo)系,你肯定很熟悉了。x 軸代表水平方向,y 軸代表垂直方向,z 軸則代表我們的目光向頁面(屏幕)看進(jìn)去的時候,各元素的布局情況。

          由于屏幕是一塊二維平面,我們實(shí)際上并沒有真的看到 z 軸,更多的是通過透視的形式。具體地說,多個元素共享同一塊二維平面時,有的元素在頂部,有的元素在底部,我們由此感受到了 z 軸的存在。

          為了決定某個元素在 z 軸方向上的位置,CSS 允許我們?yōu)?z-index 屬性設(shè)置三種值[4]

          • auto(默認(rèn)值)
          • 整數(shù)
          • inherit

          我們主要看一下整數(shù)值。它可以是正整數(shù)、負(fù)整數(shù)或者 0,值越大,元素就離我們“越近”,值越小,元素自然也就離我們“越遠(yuǎn)”。

          如果兩個元素在定位之后共享同一塊二維空間,那么在這塊空間中, z-index 越大的元素將可能覆蓋 z-index 較小的元素。

          很顯然,上面講的這些都是非常容易理解的,并且也和我們的直覺相符合。不過,下面的問題恐怕就不是很好回答了:

          • 當(dāng)設(shè)置了定位和 z-index 的元素與一個位于正常文檔流中的元素重疊時,哪一個在頂層呢?
          • 一個元素設(shè)置定位,另一個元素設(shè)置浮動,哪一個在頂層呢?
          • 如果父元素和子元素都設(shè)置了定位,會發(fā)生什么事?

          為了更好地理清這些問題,我們有必要進(jìn)一步理解與 z-index 工作原理相關(guān)的一些概念,也就是層疊上下文、層疊等級和層疊順序。

          層疊上下文和層疊等級

          針對層疊上下文和層疊等級[5] ,可能很難給出一個清晰易懂的概念,所以我們這里用通俗的例子來理解。想象一下,現(xiàn)在有一張桌子,上面擺滿了各種東西。那么這張桌子就代表了一個層疊上下文,假設(shè)還有另一張與之并排的桌子,那么就產(chǎn)生了另一個層疊上下文。

          如圖所示,層疊上下文 1 指的就是文檔根部,而層疊上下文 2 和 3 位于 1 的某個層疊等級中。此外,這兩個層疊上下文各自會包含新的層疊等級。

          現(xiàn)在想象一下,第一張桌子上面并排擺了四個磚頭,這四個磚頭上面放著一個玻璃杯,而玻璃杯上面還放著一個水果盤。那么,磚頭、玻璃杯、水果盤,各自都處于不同的層疊等級中,但它們共處于“桌子”這一層疊上下文中。

          對每一個網(wǎng)頁來說,默認(rèn)都會創(chuàng)建一個層疊上下文[6] ,這個上下文(這張桌子)的根部就是 html 元素,html 元素的所有子元素都會位于這個默認(rèn)的層疊上下文中的某個層疊等級,就好比東西會擺放在桌子的不同位置上一樣。

          當(dāng)你給某個元素設(shè)置一個非 autoz-index 時,就會創(chuàng)建一個新的 層疊上下文[7] ,它和它所包含的層疊等級都是獨(dú)立于其它層疊上下文和層疊等級的,就好比你搬了一張新的桌子放在房間里,它和舊的桌子是互相獨(dú)立的。

          層疊順序

          我們可以通過一個非常簡單的例子來理解層疊順序,這個例子甚至還不需要涉及到 定位元素[8] 。

          想象一下,現(xiàn)在有一個非常簡單的網(wǎng)頁,不考慮默認(rèn)的 , , 等元素,就只需要考慮每個網(wǎng)頁至少都會有的一個

          。在 CSS 文件中設(shè)置 html 的背景顏色為藍(lán)色,設(shè)置 div 的背景顏色為紅色,并設(shè)置寬高。

          當(dāng)加載頁面的時候,你覺得會看到什么?

          這個自然不用多想,引入眼簾的肯定是一大片的藍(lán)色,同時還有一個此前設(shè)置好尺寸的紅色塊級元素。除非你做了額外的設(shè)置,否則這個元素將正常地出現(xiàn)在左上角。

          你可能會說“就這?太簡單了吧”,不過有一個問題可能不那么簡單:為什么紅色的塊級元素就一定會位于藍(lán)色背景的上層呢?為什么我們看到的就是 div 位于 html 的上層呢?原因是,它們都遵循了層疊順序的規(guī)則。

          在這個簡單的例子中,根據(jù)規(guī)則,正常文檔流的子塊(div)的層級將會高于根元素(html)的背景和邊框。我們看到div 位于頂層,這是因?yàn)樗膶盈B等級更高。

          雖然上面這個例子只涉及到了兩個層疊等級,但實(shí)際上,在一個層疊上下文中,一共可能出現(xiàn)七個層疊等級,從最低到最高排列,依次是:

          1. 背景和邊框 :形成層疊上下文的元素的背景和邊框,它是整個上下文中層疊等級最低的。
          2. Z-Index 為負(fù)數(shù) :設(shè)置了 z-index 為負(fù)數(shù)的子元素以及由它所產(chǎn)生的層疊上下文
          3. 塊級盒模型:位于正常文檔流中的、塊級的、非定位的子元素
          4. 浮動盒模型 :浮動的、非定位的子元素
          5. 內(nèi)聯(lián)盒模型 :位于正常文檔流中的、內(nèi)聯(lián)的、非定位的子元素
          6. Z-index 為 0:設(shè)置了 z-index 為 0 的、定位的子元素以及由它所產(chǎn)生的層疊上下文
          7. Z-Index 為正數(shù) :設(shè)置了 z-index 為正數(shù)的、定位的子元素以及由它所產(chǎn)生的層疊上下文,它是整個上下文中層疊等級最高的

          這七個層疊等級就構(gòu)成了層疊順序的規(guī)則。符合層疊等級七的元素,會比層疊等級在一到六的元素更“貼近我們”,符合層疊等級五的元素,會比層疊等級二的元素更“貼近我們”,以此類推。

          第一次學(xué)習(xí)這些層疊規(guī)則的時候,我感覺收獲了很多新的東西。如果只著眼于層疊等級二、六和七(也就是涉及到 z-index 的等級),那么大部分時候,我們對于 z-index 的理解是正確的。正的 z-index 的層級比 0 要高,而 0 又比負(fù)的要高,一切都符合直覺,可能大多數(shù)人到這里就不繼續(xù)往后探究了。

          我之前就是這樣,在看到這些規(guī)則之前,以為除了正的和負(fù)的 z-index ,其它情況都可以看作是 z-index 為0 —— 不過現(xiàn)在我們很清楚了,這種想法是錯誤的。事實(shí)是,大部分元素的層級都要低于 z-index:0。

          還有一個有趣的細(xì)節(jié)是,非定位的元素實(shí)際位于四種不同的層疊等級中。乍一想覺得很奇怪,不過其實(shí)這是很合理的。假設(shè)所有的非定位元素都位于同一個層疊等級,那么我們就沒辦法在 div (塊級盒)上看到文本(內(nèi)聯(lián)盒)了。

          來看個案例

          我前面提到過很多次,當(dāng)你給一個元素設(shè)置非 auto 的 z-inde 時,會創(chuàng)建一個新的、完全獨(dú)立的層疊上下文。

          重新回顧一下之前拿桌子做比喻的案例。一開始的時候,我們的桌子上擺滿了四塊磚頭,上面是一個玻璃杯,再上面是一個水果盤?,F(xiàn)在,假設(shè)又有一張新的桌子,它擺放的東西和舊桌子差不多,唯一的不同是,新桌子少了一個水果盤。

          不難想象,舊桌子的水果盤是整個房間中位于最頂層的物品(它有最大的 z-index),不過,如果把舊桌子以及它上面的所有東西整體搬到地下室呢?此時,水果盤的層級會比新桌子上的每一個物品都要低,這是因?yàn)?,放置水果盤的舊桌子整體已經(jīng)低于新桌子了。

          對于網(wǎng)頁上的定位元素來說,其實(shí)道理是一樣的。假設(shè)有如下代碼,思考一個問題:div.twodiv.four,哪個在上哪個在下?

          HTML:

          <div?class="one">
          ??<div?class="two">div>
          ??<div?class="three">div>
          div>
          <div?class="four">div>

          CSS:

          div?{
          ??width:?200px;
          ??height:?200px;
          ??padding:?20px;
          }
          ?
          .one,?.two,?.three,?.four?{
          ??position:?absolute;
          }
          ??
          .one?{
          ??background:?#f00;
          ??outline:?5px?solid?#000;
          ??top:?100px;
          ??left:?200px;
          ??z-index:?10;
          }
          ??
          .two?{
          ??background:?#0f0;
          ??outline:?5px?solid?#000;
          ??top:?50px;
          ??left:?75px;
          ??z-index:?100;
          }
          ?
          .three?{
          ??background:?#0ff;
          ??outline:?5px?solid?#000;
          ??top:?125px;
          ??left:?25px;
          ??z-index:?150;
          }
          ?
          .four?{
          ??background:?#00f;
          ??outline:?5px?solid?#ff0;
          ??top:?200px;
          ??left:?350px;
          ??z-index:?50;
          }

          盡管 div.two 有更高的 z-index(100),但在頁面上,它的層級實(shí)際上比 div.fourz-index 為50)要低。下圖就是頁面元素的層級情況,根據(jù)黑色和黃色邊框,我們可以區(qū)分每個元素生成的不同的層疊上下文。

          由于 div.two ?位于 div.one 中,所以它的 z-index 是和 div.one 的層疊上下文相關(guān)的,也就是說,實(shí)際表現(xiàn)出來的 z-index 是下面這樣的:

          • .one —— z-index = 10
          • .two —— z-index = 10.100
          • .three —— z-index = 10.150
          • .four —— z-index = 50

          div.one 和內(nèi)部包含的一切將會在層級上低于 div.four,無論給 ?div.one 的子元素設(shè)置多大的 z-index,子元素的層級都無法超過 div.four。

          看到這個例子是不是有一種熟悉的味道?我也曾經(jīng)被 z-index 這么坑過一兩次。我們都曾疑惑一個問題,為什么一個 z-index 非常大的元素,在層級上始終無法超過一個 z-index 比它小很多的元素?相信在學(xué)習(xí)了這些案例之后,你已經(jīng)豁然開朗了。

          總結(jié)

          在最初學(xué)習(xí) z-index 的時候,我們都會認(rèn)為它很簡單,這不就是代表元素在 z 軸上的位置嗎?不過我們現(xiàn)在知道了,事情遠(yuǎn)沒有這么簡單。深入理解 z-index[9] 一文也揭示了 z-index 背后一些原理層面的東西,包括層疊上下文,層疊等級以及一系列決定元素的層疊順序的規(guī)則。

          最后,記住一個很重要的結(jié)論:定位元素可以創(chuàng)建新的層疊上下文,在這個上下文中的所有層疊等級,都會高于或者低于另一個層疊上下文的所有層疊等級。

          拓展閱讀

          • What No One Told You About Z-Index by Philip Walton
          • The Z-Index CSS Property: A Comprehensive Look on Smashing Magazine
          • How Well Do You Understand CSS Positioning?
          • The stacking context on Mozilla Developer Network
          • Z-Index And The CSS Stack: Which Element Displays First?

          參考資料

          [1]

          定位方案: https://www.w3.org/TR/CSS2/visuren.html#positioning-scheme

          [2]

          z-index 屬性: http://www.w3.org/TR/CSS2/visuren.html#layers

          [3]

          z-index: http://www.vanseodesign.com/css/css-stack-z-index/

          [4]

          z-index 屬性設(shè)置三種值: http://www.w3.org/TR/CSS21/visuren.html#propdef-z-index

          [5]

          層疊上下文和層疊等級: http://timkadlec.com/2008/01/detailed-look-at-stacking-in-css/

          [6]

          層疊上下文: https://developer.mozilla.org/en-US/docs/Web/Guide/CSS/Understanding_z_index/The_stacking_context

          [7]

          層疊上下文: http://www.w3.org/TR/CSS21/zindex.html

          [8]

          定位元素: http://www.vanseodesign.com/css/css-positioning/

          [9]

          深入理解 z-index: http://coding.smashingmagazine.com/2009/09/15/the-z-index-css-property-a-comprehensive-look/

          瀏覽 47
          點(diǎn)贊
          評論
          收藏
          分享

          手機(jī)掃一掃分享

          分享
          舉報
          評論
          圖片
          表情
          推薦
          點(diǎn)贊
          評論
          收藏
          分享

          手機(jī)掃一掃分享

          分享
          舉報
          <kbd id="afajh"><form id="afajh"></form></kbd>
          <strong id="afajh"><dl id="afajh"></dl></strong>
            <del id="afajh"><form id="afajh"></form></del>
                1. <th id="afajh"><progress id="afajh"></progress></th>
                  <b id="afajh"><abbr id="afajh"></abbr></b>
                  <th id="afajh"><progress id="afajh"></progress></th>
                  最新中文字幕2019视频在线不卡 | 青草久视频 | 人妻巨大乳HD免费看 | 亚洲无码视频专区 | 日P视频网站 |