前端--关于CSS盒模型
CSS樣式規(guī)則的學(xué)習(xí)是很繁瑣和枯燥的,因為它不像物理、數(shù)學(xué)或者其他編程語言一樣有一些基本概念、有一些基本公理或者規(guī)則,其他所有的表現(xiàn)都是概念在這些公里或者規(guī)則之下的邏輯游戲,CSS是有一些基本概念,但它沒有說給你幾條規(guī)則然后所有的表現(xiàn)都是在這些規(guī)則之下的任意自由組合,你要推測一個樣式聲明塊的在頁面中具體是怎樣表現(xiàn)的,你幾乎靠非常少是靠邏輯推理去推測出來,絕大多數(shù)是你知道并記住了這種寫法的聲名塊是具有怎樣的表現(xiàn)的。之所以為這樣也是因為樣式的組合太繁瑣組合情況特別多,像同樣的概念margin在塊級中的表現(xiàn)和在行內(nèi)元素中的表現(xiàn)是不一樣的,即便是同樣在塊級元素中不同方向上的margin表現(xiàn)也是不一樣的,再進(jìn)一步就算是同樣在塊級元素中同樣的方向上,父元素的某些屬性不同其表現(xiàn)也是不一樣的,再加上浮動定位又是另一種情況,要是再考慮到各種不同瀏覽器的兼容性的話那就更令人煩躁了,這樣的特性是不可能存在一個或幾個規(guī)則讓你邏輯推理樣式表現(xiàn)的,掌握CSS樣式規(guī)則只有窮舉各種各樣的組合并且記住它們的表現(xiàn)(雖然可能會有一小點的邏輯推理),因此前端這個職業(yè)感覺工作經(jīng)驗比其他的編程語言更加重要一些。
掌握一門語言的結(jié)果是在頭腦中可以形成一個清晰的知識系統(tǒng)脈絡(luò)圖,而CSS的學(xué)習(xí)很難有一個清晰的邏輯線路去循環(huán)漸進(jìn)的學(xué)習(xí),因為它的概念關(guān)聯(lián)性太弱了,所以在沒有很清晰的邏輯幫助理解概念時,很好的理解現(xiàn)有概念是非常有必要的,比如說盒模型。
盒模型以及相關(guān)知識點在CSS中占有非常重要而核心的地位,而大家常常聽到的非常經(jīng)典的對盒模型的理解就是一個盒子的類比,盒子本身是border,里面貨物就是內(nèi)容,填充就是padding,盒子在擺放的時候要分開一定的距離就是margin。這種類比有它的好處,但是仍然感覺像是和沒說一樣(至少我這么覺得)。而且這種類比無形中把padding和內(nèi)容這個整體視為標(biāo)簽元素的內(nèi)容,把margin視為內(nèi)容以外的東西,感覺這對理解css布局的相關(guān)本質(zhì)會造成一定的偏差,最明顯的一個例子就是初學(xué)人員會完全沒有意識到width和height指定的寬和高是內(nèi)容的寬和高(css3加了新的屬性可以更改寬高的指定范圍),并不是把padding和border還有margin算在一起的。所以現(xiàn)在我并不想把內(nèi)容、padding、border、margin放到一個盒子相關(guān)中去理解,以一個不是盒模型的角度去理解也同樣可能(只是可能因人而異)有利于避開在盒模型類比下形成想當(dāng)然的認(rèn)識。
在起初接觸前端的時候都會看到這樣的話:html標(biāo)記頁面內(nèi)容,css表現(xiàn)頁面樣式,javascript控制頁面行為。這是說頁面的內(nèi)容都是用html標(biāo)簽標(biāo)記出來的,一個內(nèi)容一定有一個相關(guān)html標(biāo)簽去標(biāo)記它;css做到的是表現(xiàn)與內(nèi)容分離,也就是說css是為頁面的內(nèi)容添加各種各樣的樣式,它的操作目標(biāo)是內(nèi)容,所以關(guān)于CSS的概念以內(nèi)容為起點討論,而不以盒子為起點。
打開網(wǎng)頁可以發(fā)現(xiàn)頁面的內(nèi)容范圍是文字、表單相關(guān)(輸入框、按鈕、單選框、復(fù)選框、下拉框)、圖片、音頻、視頻。內(nèi)容在頁面中會放到一個矩形區(qū)域中即內(nèi)容區(qū),控制該區(qū)域的寬高屬性為width和height,在內(nèi)容區(qū)外部分則是標(biāo)簽元素形成的用于布局用的額外的空間。
標(biāo)記這些內(nèi)容的html標(biāo)簽分為兩種:替換元素與非替換元素。
替換元素:以上除了文字都是替換元素,替換元素是指這個標(biāo)簽元素為某個內(nèi)容的占一個位子,在原始html代碼中看不出來實際具體表現(xiàn)。像圖像、音頻、視頻標(biāo)簽它們就是指向某個圖片文件、音頻文件、視頻文件。起占位作用的標(biāo)簽就是一種替換元素。
非替換元素:標(biāo)簽元素標(biāo)記的內(nèi)容在原始html代碼中可以看出來,就不如說用span標(biāo)簽標(biāo)記的文本。標(biāo)記文本的span標(biāo)簽就是一種非替換元素。
因為內(nèi)容總是有一個標(biāo)簽來標(biāo)記它,而標(biāo)簽在瀏覽器中的渲染結(jié)果就是在內(nèi)容周圍變成一個矩形區(qū)域(在CSS3中可以設(shè)置為非矩形區(qū)域),這種矩形區(qū)域會在內(nèi)容周圍生成額外的空間,而產(chǎn)生的額外空間的種類一共有三種:padding(內(nèi)邊距)、border(邊框)、margin(外邊距)。在正常文檔流中css對內(nèi)容的樣式布局實現(xiàn)大部分就是通過設(shè)置padding、border、margin來實現(xiàn)的。
padding空間是在邊框和內(nèi)容區(qū)域之間的無色透明的一塊區(qū)域,該區(qū)域可以看到元素的背景色并且在沒有border和margin的情況下該區(qū)域是不能合并的。
border空間是在內(nèi)邊距和外邊距之間的一塊有內(nèi)置樣式有顏色的一塊區(qū)域,該區(qū)域也是繪制在背景色之上的,因此如果邊框有鏤空是可以看到背景顏色的。
margin空間是在邊框外面的一塊無色透明區(qū)域,該區(qū)域可以看到父元素的背景色并且在正常流中垂直方向上該區(qū)域是可以合并的,水平方向上是不存在合并規(guī)則的。
以上三個空間區(qū)域在在默認(rèn)情況下都是不存在的。
雖然每個元素都會在內(nèi)容周圍渲染成矩形區(qū)域,但不同元素默認(rèn)渲染成的矩形區(qū)域類型可能是不同的。通過設(shè)置display可以在不同類型的矩形區(qū)域之間進(jìn)行切換。對矩形區(qū)域分類的一個標(biāo)準(zhǔn)就是看矩形區(qū)域前后是否有換行符:前后都有換行符的矩形區(qū)域為塊級矩形區(qū)域;前后沒有換行符的矩形區(qū)域為行內(nèi)矩形區(qū)域。相應(yīng)的不同類別的矩形區(qū)域所對應(yīng)的元素也就叫做塊級元素或者行內(nèi)元素。換行符只是塊級和行內(nèi)與否的一條區(qū)分標(biāo)識,并不是區(qū)別的全部,他倆在默認(rèn)狀態(tài)和變化行為上也有些許差別。
在文檔流中默認(rèn)狀態(tài)下,多個塊級元素是垂直排列的,并且它的寬為父元素的內(nèi)容區(qū)域?qū)?#xff0c;高為自己內(nèi)容區(qū)域高,可以自由改變自己內(nèi)容區(qū)的寬和高。而多個行內(nèi)元素是橫向排列的,它的寬和高都為內(nèi)容區(qū)域的寬和高,并且不能設(shè)置內(nèi)容區(qū)的寬和高。
這樣,一塊標(biāo)簽標(biāo)記的內(nèi)容在頁面中的表現(xiàn)從里到外就是內(nèi)容區(qū)、內(nèi)邊距、邊框、外邊距四部分,這四部分是緊密相連的,并作為一個整體放在一個布局上下文中,并基于這個布局上下文擺放。布局上下文是父元素的內(nèi)容區(qū),這個內(nèi)容區(qū)可能在塊級元素中也可能在行內(nèi)元素中。一般情況下,各個標(biāo)簽內(nèi)容能按照從左到右的順序擺放的就按照從左到右的順序擺放,從左到右擺放不下的(像超出或者有換行符)就按照從上到下的順序擺放,如果一個元素標(biāo)簽處在這樣一個擺放順序中,就說這個標(biāo)簽在文檔流中。只有浮動和定位會擺脫這種束縛,這時就說元素脫離了文檔流。
?
矩形區(qū)域中各個屬性的取值只有margin可以取負(fù)值,只有width和margin可以取auto關(guān)鍵字,border不能為百分?jǐn)?shù),其他屬性都只能取 正的數(shù)字或者正的百分?jǐn)?shù)。其中margin和padding設(shè)置的值是一個塊區(qū)域的垂直高度,這塊區(qū)域的長和寬是隨著內(nèi)容的width和height變化 而變化的。border設(shè)置的是自身的寬度,其長度也是隨著相應(yīng)邊的長度變化而變化的。padding和border的取值是不會根據(jù)某些條件自動改變 的,一旦設(shè)置就不會發(fā)生改變。margin的取值雖然可以自動變化,但產(chǎn)生變化的條件一般都是空間受限。取值可以根據(jù)內(nèi)容變化而變化的只有width和 height屬性,前提是width、height取值為auto。下面根據(jù)塊級和行內(nèi)分開討論,并在各種情況下再根據(jù)水平方向和垂直方向分開討論。
1.塊級矩形區(qū)域中:
在 水平方向上,如果width沒有設(shè)置固定值即值為auto的時候,width屬性有盡可能寬的傾向,比如若width和margin同時設(shè)置為auto, 那么margin的值會被瀏覽器重置為0。如果為width設(shè)定了固定值,那么它的值就是固定的了,不論是否脫離文檔流是否超出了父元素的內(nèi)容區(qū)。
1. 當(dāng)width設(shè)置為auto的時候,這種情況下width有一條原則:若該內(nèi)容區(qū)在布局上下文中(父元素的內(nèi)容區(qū))則它的width會盡可能的大。若該內(nèi) 容區(qū)因為正的margin的原因全部超過了布局上下文,或者padding、border大于了布局上下文的寬,那么它的width取值是為0的,雖然 width為0,但內(nèi)容還是存在的并且padding和border屬性值也都是不會改變的。但還存在一種情況,就是當(dāng)padding和margin同時 存在的時候,正數(shù)的margin-right不能使元素的矩形區(qū)域離開父元素的內(nèi)容區(qū),其數(shù)值再大也無效。而正數(shù)的margin-left可以是元素的矩 形區(qū)域離開父元素的內(nèi)容區(qū)。另外一條特殊性原則就是當(dāng)margin為負(fù)的情況了,負(fù)數(shù)產(chǎn)生的效果就是把內(nèi)容區(qū)穿過布局上下文并往布局上下文外側(cè)移動相應(yīng)的 距離。當(dāng)一側(cè)margin為負(fù)數(shù)的時候,并還存在三種可能情況:另一側(cè)margin沒有數(shù)值、另一側(cè)margin有正值、另一側(cè)marging有負(fù)值。 另一側(cè)margin沒有值的時候,width會一直延伸。另一側(cè)margin有正值的時候,根據(jù)正數(shù)的大小,以負(fù)數(shù)margin位置和正數(shù)margin位 置為內(nèi)容區(qū)的兩邊,自動調(diào)整width的大小,當(dāng)正數(shù)margin延伸的位置與負(fù)數(shù)margin所在的位置重合的時候,width變?yōu)?。另一側(cè) margin有負(fù)值的時候,內(nèi)容區(qū)兩邊向布局上下文外側(cè)左右延伸。
2.當(dāng)width設(shè)置為固定值的時候,這種情況看起來復(fù)雜度低一些,畢竟可以自 己改變的量只剩下了margin。此時如果在內(nèi)容區(qū)兩邊同時添加左右padding是不會有任何沖突的,但是若同時添加左右margin就很可能產(chǎn)生沖突 了。因為width是固定的,若固定一邊的margin,那么另一邊的margin也會是固定的,但另一邊的固定的值很可能不是你設(shè)置的那個值。這時候這 個矩形區(qū)域就會受限,首先的處理方法就是有一個優(yōu)先級,如果左右margin相互沖突,那么優(yōu)先滿足左邊的margin,如果上下margin相互沖突, 那么優(yōu)先滿足上面的margin。像固定寬度的情況下兩邊都是負(fù)數(shù)的margin,那么元素會優(yōu)先向左邊移動。還有一個特殊用法是關(guān)于水平居中,即當(dāng)左右 兩邊margin設(shè)置為auto,并且width為固定值,則該內(nèi)容區(qū)域在布局上下文中水平居中。
左右負(fù)外邊距還有一個特殊的規(guī)則,就是如果左外 邊距為負(fù)數(shù),并且元素都超出了瀏覽器,那么它就真的超出看不見了,不會在瀏覽器下面形成滾動條。如果右外邊距為負(fù)數(shù),并且元素向外移動超出了瀏覽器,那么 它是不會消失看不見的,因為會在瀏覽器下面形成滾動條。還有在正常情況下,漢字在父元素高度允許的情況下會自動換行,若父元素的高不足以容納所有漢字,并 且父元素也沒有設(shè)置over-flow屬性,那么漢字內(nèi)容就會超出父元素。而單詞要想換行的話除了父元素高度要允許,還是額外設(shè)置word-wrap和 word-break屬性。
在垂直方向上,垂直方向上的情況比水平方向上的還要復(fù)雜一些,因為margin在垂直方向上可以合并而在水平 方向上是不會合并的。垂直方向上的height屬性不會像width一樣默認(rèn)情況下會盡量延展,而是會盡量雖小剛好為內(nèi)容高度。這樣在height為 auto,并且父元素沒有adding和border空間的時候,最高塊級子元素和最低塊級子元素的margin范圍是不會在父元素的內(nèi)容區(qū)內(nèi)的,它倆 margin作用范圍和父元素的margin是一樣的(都是父元素外的margin空間),并且有合并效果。如果父元素有border或者 padding,那么這倆空間就會阻擋最高和最低塊級子元素的margin作用范圍超出其布局上下文,并會增加父元素的height數(shù)值。還要注意若 padding或margin設(shè)置為了百分?jǐn)?shù),那么不管垂直還是水平方向這百分?jǐn)?shù)的參照都是父元素的width。在一個布局上下文中,其中的各個塊級子元 素之間的相對位置是一定的,如果一個子元素位置發(fā)生了變化,那么它下面的子元素為了維持和原來一樣的相對位置也會隨著產(chǎn)生相應(yīng)的位置變化。這在負(fù)的外邊距 情況下要特別注意,負(fù)的外邊距根據(jù)父元素的height是否為auto表現(xiàn)的也不是很一樣。這種不一樣主要表現(xiàn)在最后一個塊級子元素上,前面說過當(dāng) margin-top的值和margin-bottom的實現(xiàn)沖突的時候要優(yōu)先實現(xiàn)margin-top的值,因為塊級子元素在布局上下文中根據(jù) margin可以自由調(diào)整位置的,所以第一個和中間的子元素是不存在margin-top和margin-bottom沖突的情況的,唯一可以出現(xiàn)沖突的 情況就是最后一個塊級子元素,因為最后一個塊級子元素的margin-bottom是對父元素內(nèi)容區(qū)的下邊界產(chǎn)生作用的,如果這個下邊界可變就沒有沖突, 如果這個下邊界不可變就可能會有沖突,這個下邊界可變與不可變就是父元素的height是否為auto決定的。當(dāng)height為auto的時候,塊級子元 素所有的負(fù)的margin都會產(chǎn)生父元素變短的效果,若height為固定值,那么最后一個塊級子元素的margin-bottom不會有任何作用。
2.行內(nèi)矩形區(qū)域中:
行 內(nèi)矩形區(qū)域(盒模型)就簡單一些了。首先行內(nèi)矩形區(qū)域的width和height的設(shè)置是無效的,它只會根據(jù)內(nèi)容的大小自動調(diào)整自己的大小。在外邊距方 面,margin的垂直設(shè)置是不會有任何效果的,因為它畢竟在行框內(nèi),margin改變不了行間距。而水平的margin是可以有相應(yīng)的效果的。同樣的 padding,border的垂直設(shè)置也同樣是不會改變行間距的,因此看不出效果,除非有背景或者顏色會有一些效果,比如說會遮蓋住相鄰上下兩行的內(nèi) 容,但行間距還是沒有改變的。水平設(shè)置倒是也同樣會有相應(yīng)的效果。
轉(zhuǎn)載于:https://www.cnblogs.com/jinjilin/p/5047255.html
總結(jié)
以上是生活随笔為你收集整理的前端--关于CSS盒模型的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 因xhost命令和DISPLAY环境变量
- 下一篇: Word中更新交叉引用