形狀 一 自適應的橢圓 1.難題 1> 圓 你可能註意到過, 給任何正方形元素設置一個足夠大的border-radius, 就可以把它變成一個圓形。所用到的CSS 代碼如下所示: *當任意兩個相鄰圓角的半徑之和超過border box 的尺寸時,用戶 代理必須按比例減小各個邊框半徑所使用的值,直到它 ...
形狀
一 自適應的橢圓
1.難題
1> 圓
你可能註意到過, 給任何正方形元素設置一個足夠大的border-radius,
就可以把它變成一個圓形。所用到的CSS 代碼如下所示:
1 #bd { 2 width: 200px; 3 height: 200px; 4 background: #fb3; 5 border-radius: 100px; /* >= 正方形邊長的一半 */ 6 }
*當任意兩個相鄰圓角的半徑之和超過border box 的尺寸時,用戶
代理必須按比例減小各個邊框半徑所使用的值,直到它們不會相互重疊
為止
2> 橢圓
如果它的寬高相等,就顯示為一個圓;如果寬
高不等,就顯示為一個橢圓
2.解決方案
說到border-radius,有一個鮮為人知的真相:它可以單獨指定水平
和垂直半徑,只要用一個斜杠(/)分隔這兩個值即可。這個特性允許我
們在拐角處創建橢圓圓角
因此,如果我們有一個尺寸為
200px × 150px 的元素,就可以把它圓角的兩個半徑值分別指定為元素寬高的
一半,從而得到一個精確的橢圓:
#bd { width:200px; height:100px; border-radius:100px/50px; }
但是,這段代碼存在一個很大的缺陷:只要元素的尺寸發生變化,
border-radius 的值就得跟著改。我們在圖3-5 中可以看到,當元素的尺寸
變為200px×300px 時,如果border-radius 沒有跟著改變,會發生什麼後
果。因此,如果我們的元素尺寸會隨著它的內容變化而變化,這就是一個問
題了。
它不僅可以接受長度值,還可以接受百分比值
這個百分比值會基於元素的尺寸進行解析,即寬度用於水平半徑的解析,而高度
用於垂直半徑的解析。這意味著相同的百分比可能會計算出不同的水平和垂
直半徑。
#bd { border-radius:50%; }
3.半橢圓
我們甚至可以為所有四個角提供完全不同的水平和垂
直半徑,方法是在斜杠前指定1~4 個值,在斜杠後指定另外1~4 個值。請註
意這兩組值是單獨展開為四個值的。舉例來說,當border-radius 的值為
10px / 5px 20px 時,其效果相當於10px 10px 10px 10px / 5px 20px
5px 20px。
#bd { border-radius:50%/100% 100% 0 0; }
半橢圓是可以變成半圓的,只要它的寬度剛好伸展到高度的兩倍(或者對一個沿縱軸劈開的
橢圓來說,是高度伸展為寬度的兩倍
4.四分之一橢圓
要創建一個四分之一橢圓,其中一個角的水平和垂直半徑值都需要是
100%,而其他三個角都不能設為圓角。
#bd { border-radius:100% 0 0 0; }
二 平行四邊形
1.難題
使用skew()來進行斜向拉伸實現 平行四邊形
一個參數時:表示水平方向的傾斜角度
兩個參數時:第一個參數表示水平方向的傾斜角度,第二個參數表示垂直方向的傾斜角度
#box { transform:skew(-45deg); }
但是,這導致它的內容也發生了斜向變形,這很不好看,而且難讀。
有沒有辦法只讓容器的形狀傾斜,而保持其內容不變呢?
2.且套元素方案
我們可以對內容再應用一次反向的skew() 變形,從而抵消容器的變形
效果,最終產生我們所期望的結果。
<a href="#yolo" class="button"> <div>Click me</div> </a> <style> .button { transform: skewX(-45deg); } .button > div { transform: skewX(45deg); } </style>
3.偽元素方案
另一種思路是把所有樣式(背景、邊框等)應用到偽元素上,然後再對
偽元素進行變形。因為我們的內容並不是包含在偽元素里的,所以內容並不
會受到變形的影響。下麵來看看這個技巧能否得到與前面相同的鏈接樣式。
此時,用偽元素生成的方塊是重疊在內容之上 可以給偽元素設置z-index: -1 樣式
.button { width:200px; height:200px; position: relative; /* 其他的文字顏色、內邊距等樣式…… */ } .button::before { content: ''; /* 用偽元素來生成一個矩形 */ position: absolute; top: 0; right: 0; bottom: 0; left: 0; width:inherit; height:inherit; z-index: -1; background: #58a; transform: skew(45deg); }
三 棱形圖片
1.難題
使用rotate()
2.基於變形的方案
需要把圖片用一個<div> 包裹起來,然後對其應用相反的rotate()
變形樣式:
<div class="picture"> <img src="adam-catlace.jpg" alt="..." /> </div>
.picture { width: 400px; transform: rotate(45deg); overflow: hidden; } .picture > img { max-width: 100%; transform: rotate(-45deg); }
以上產生一個 八角形 的圖片 並沒有產生棱形
可以使用scale()解決:
.picture { width: 400px; transform: rotate(45deg); overflow: hidden; } .picture > img { max-width: 100%; transform: rotate(-45deg) scale(1.42); }
3.裁切路徑方案
上面的方法確實可以奏效,但它基本上是一個hack。這個方法需要一層
額外的HTML 標簽,這不夠簡潔;代碼本身也不夠直觀;它甚至還不夠健
壯——如果我們碰巧要處理一張非正方形的圖片,這個小把戲就會原形畢露
事實上,我們還有一個更好的辦法來完成這個任務。它的主要思路是
使用clip-path 屬性。
裁切路徑允許我們把元素裁剪為我們想要的任何形狀。在這個例子
中,我們將會使用polygon()(多邊形)函數來指定一個菱形。實際上,它
允許我們用一系列(以逗號分隔的)坐標點來指定任意的多邊形。我們甚至
可以使用百分比值,它們會解析為元素自身的尺寸。代碼如下所示:
-webkit-clip-path: polygon(50% 0, 100% 50%, 50% 100%, 0 50%);
四 切角效果
1.難題
2.解決方案
1> 利用漸變
右下角:
#box { background: #58a; background: linear-gradient(-45deg, transparent 15px, #58a 0); }
四角:
#box { background: #58a; background: linear-gradient(135deg, transparent 15px, #58a 0) top left, linear-gradient(-135deg, transparent 15px, #58a 0) top right, linear-gradient(-45deg, transparent 15px, #58a 0) bottom right, linear-gradient(45deg, transparent 15px, #58a 0) bottom left; background-size: 50% 50%; background-repeat: no-repeat; }
3.弧形切角
可以用來創建弧形切角(很多人也把這種
效果稱為“內凹圓角”,因為它看起來就像是圓角的反向版本)。唯一的區別
在於,我們會用徑向漸變來替代上述線性漸變:
#box { background: #58a; background: radial-gradient(circle at top left, transparent 15px, #58a 0) top left, radial-gradient(circle at top right, transparent 15px, #58a 0) top right, radial-gradient(circle at bottom right, transparent 15px, #58a 0) bottom right, radial-gradient(circle at bottom left, transparent 15px, #58a 0) bottom left; background-size: 50% 50%; background-repeat: no-repeat; }
五 梯形標簽頁
1.難點
一直以來,梯形
都是眾所周知難以用CSS 生成的形狀,
2.解決方案
transform: perspective(.5em) rotateX(5deg);
整個元素應用3D 變形的,因此它上面的文字也變形了。對元素使用了3D
變形之後,其內部的變形效應是“不可逆轉”的,這一點跟2D 變形不同
(在2D 變形的體系之下,內部的逆向變形可以抵消外部的變形效應)
唯一可行的途徑就是把變形效果作用在偽元
素上。
.tab { position: relative; display: inline-block; padding: .5em 1em .35em; color: white; } .tab::before { content: ''; /* 用偽元素來生成一個矩形 */ position: absolute; top: 0; right: 0; bottom: 0; left: 0; z-index: -1; background: #58a; transform: perspective(.5em) rotateX(5deg); }