1. 程式人生 > >CSS進階(14)—— position:absolute如此高深,我當真不懂(下)

CSS進階(14)—— position:absolute如此高深,我當真不懂(下)

  上章我們聊了和absolute的流體特性以及和absolute搭配使用的CSS屬性,本章我們就來聊一聊position家族的另外兩大成員——relative和fixed。

 

1.relative的定位(不推薦使用)

  理論上relative/absolute/fixed都能對absolute的"包裹性"以及"定位"產生限制,但只有relative能使得元素保持在正常的文件流中,因此我們往往使用absoluted搭配relative使用。之前講到,left/right/top/bottom是定位家族的特有屬性,因此relative也支援定位,且relative定位有兩大特性:一是相對自身定位,二是“無侵入”。為了更好的展示relative的特性,我們引入absolute元素進行對比。

  測試一:left:0,top:0;

<!-- relative定位測試 -->
<div class="container">
	<div class="relative">relative</div>
	<div class="absolute">absolute</div>
</div>
<style>
.container{
	width: 200px;
	height: 200px;
	background: #999999;
	padding:100px;
	border:5px solid red;
	position: relative;
}
.relative{
	width: 100px;
	height: 100px;
	background: green;
	position: relative;
	left: 0;
	top: 0;
}
.absolute{
	width: 100px;
	height: 100px;
	background: yellow;
	position: absolute;
	left: 0;
	top: 0;
}
</style>

  第一個測試,absolute元素的包含塊是父元素的padding-box,因此absolute移到包含塊左上角,而relative元素紋絲不動。

  測試二:left:100px;top:100px;

 測試二的結果表明relative元素是相對於自身發生偏移的,也就是說relative的偏移位置跟他原來所處的位置有關,也就是第一個特性——相對自身定位。

  測試三:加入吃瓜群眾。

  relative定位前:

<!-- relative定位測試 -->
<div class="container">
	<div class="">我是一個吃瓜群眾</div>
	<div class="relative">relative</div>
	<!-- <div class="absolute">absolute</div> -->
	<div class="">我是一個吃瓜群眾</div>
</div>
<style>
.container{
	width: 200px;
	height: 200px;
	background: #999999;
	padding:100px;
	border:5px solid red;
	position: relative;
}
.relative{
	width: 100px;
	height: 100px;
	background: green;
	position: relative;
	/*left: 100px;
	top: 100px;*/
}
.absolute{
	width: 100px;
	height: 100px;
	background: yellow;
	position: absolute;
	left: 100px;
	top: 100px;
}
</style>

  

  relative定位後

<!-- relative定位測試 -->
<div class="container">
	<div class="">我是一個吃瓜群眾</div>
	<div class="relative">relative</div>
	<!-- <div class="absolute">absolute</div> -->
	<div class="">我是一個吃瓜群眾</div>
</div>
<style>
.container{
	width: 200px;
	height: 200px;
	background: #999999;
	padding:100px;
	border:5px solid red;
	position: relative;
}
.relative{
	width: 100px;
	height: 100px;
	background: green;
	position: relative;
	left: 100px;
	top: 100px;
}
.absolute{
	width: 100px;
	height: 100px;
	background: yellow;
	position: absolute;
	left: 100px;
	top: 100px;
}
</style>

  

  可以發現:relative元素相對於自身定位前後,吃瓜群眾的位置保持不變,只有relative相對於自身發生了偏移,因此relative是一種無侵入的定位,不會影響其他元素原來的佈局行為。

  除此之外,relative定位還有兩個點值得一提,首先是相對定位元素的left/right/top/bottom的百分比值是相對於包含塊進行計算的,還有一點是當relative元素同時出現相同方向上的定位時(如left:0,right:0)不會保持absolute的拉伸特性,而是取文件流方向的一邊作為唯一值,也就是隻保留left和top。

  在測試三中,我們看到了一個層疊現象,由於relative元素的層疊順序是"鬼畜"級別的(我也不懂這是什麼意思),因此作者不建議使用relative進行定位。因此relative幾乎可以看作是absolute的附屬css了。

2.無依賴固定定位(fixed)

  position:fixed的固定定位元素的"包含塊"是根元素(近似<html>),也就是除了根元素沒人能限制fixed元素不知你是否還記得無依賴絕對定位的特性,下面我們來測試一下,是否有無依賴固定定位。

<!-- 無依賴固定定位 -->
<div class="container">
	<span>隨便說兩句</span>
	<div class="fixed"></div>
</div>
<style type="text/css">
.container{
	width: 200px;
	height: 200px;
	background: #999999;
	padding:100px;
	border:5px solid red;
}
.fixed{
	width: 100px;
	height: 100px;
	background: green;
	position: fixed;
}
</style>

  經過測試,確實存在無依賴固定定位,且表現和無依賴絕對定位“相同”。那麼知道了這個特性有什麼用呢?個人認為,沒什麼軟用,既然用了固定定位,就是要利用其依賴跟元素進行定位,所以無依賴固定定位也就沒什麼軟用了。

3.利用fixed固定定位生成滾動條鎖定的彈窗

  通常情況下,彈窗功能需要依託瀏覽器進行定位,而不是某個元素,因為我們希望彈窗總能出現在螢幕的“居中”位置,要實現這個功能非常簡單,只需要用到固定定位即可。

<!-- 固定定位生成彈窗 -->
<div class="fixed">
	<div>我是彈窗</div>
</div>
<style>
html,body{
	margin: 0;
	height: 200%;
	background-image: url('../小和尚.jpg');
}
.fixed{
	position: fixed;
	top: 0;
	bottom: 0;
	right: 0;
	left: 0;
	background: rgba(0,0,0,0.5);
	margin: auto;
}
.fixed div{
	position: absolute;
	right: 0;
	top: 0;
	left: 0;
	bottom: 0;
	width: 40%;
	height: 30%;
	background: #fff;
	margin: auto;
	overflow: auto;
}
</style>

  

 我們實現了居中效果,但還有一個麻煩就是fixed元素的包含塊是html,因此html的內容有滾動條的時候,在彈窗頁面我們依舊可以控制html滾動條的滾動,這樣的使用者體驗並不好。

  因此如果我們需要一個滾動條固定的彈窗效果,必須讓滾動條不在html上,我們可以在html下面生成一個父級容器,讓父級容器來生成滾動條,這樣就不會影響fixed固定定位了。如下所示

<!-- 固定定位生成不能滾動的彈窗 -->
<div class="father">
	<div style="height: 200%;background: url('../小和尚.jpg');">我來生成滾動條</div>
	<div class="fixed">
		<div>我是彈窗</div>
	</div>
</div>
<style>
html,body{
	margin: 0;
	height: 100%;
	overflow: hidden;
}
.father{
	height: 100%;
	overflow: auto;
}
.fixed{
	position: fixed;
	top: 0;
	bottom: 0;
	right: 0;
	left: 0;
	background: rgba(0,0,0,0.5);
	margin: auto;
}
.fixed div{
	position: absolute;
	right: 0;
	top: 0;
	left: 0;
	bottom: 0;
	width: 40%;
	height: 30%;
	background: #fff;
	margin: auto;
	overflow: auto;
}
</style>