成人免费xxxxx在线视频软件_久久精品久久久_亚洲国产精品久久久_天天色天天色_亚洲人成一区_欧美一级欧美三级在线观看

萬能的CSS 漸變!單標簽繪制一個足球場

開發 前端
漸變是 CSS 中非常強大但比較繁瑣的功能了,幾乎是萬能的,能夠設計出來的都可以通過漸變繪制出來,只是實現的復雜度問題,擅于發現圖形的規律也能有效地減少漸變的復雜度。

世界杯正在進行中,也不要忘記學習 CSS(得想辦法蹭一波熱度)。比如,用 CSS 繪制一個足球場?

圖片

CSS 足球場

一眼望去,這里的形狀只有圓形和矩形,在不借助其他標簽的情況下(包括偽元素),其實很容易聯想到漸變,一起看看如何繪制的吧,有非常多的漸變小技巧~

溫馨提示:文章中帶有“??”的描述屬于足球小知識,不感興趣的可以跳過,與 CSS 無關。

一、場地的尺寸設計

首先來看一下足球場的構造,下面是在網上找到的一張設計圖。

圖片

球場設計圖

主要有以下幾個部分:

  1. 整體是矩形,邊線和底線,長度是 109~131碼(90~120m),寬度是 49-98碼(45~90m)。
  2. 中線,貫穿球場。
  3. 開球點,位于中線的中心。
  4. 中圈,以開球點為圓形,半徑為 10碼(9.15m)圓。
  5. 罰球區(大禁區),長度是44碼(40.3m),寬度是18碼(16.5m)。
  6. 球門區(小禁區),長度是20碼(18.3m),寬度是6碼(5.5m)。
  7. 球門,長度是8碼(7.32m)。
  8. 罰球點(點球點),距離球門12碼(11m)。
  9. 罰球弧(禁區弧),以罰球點為圓心,半徑為 10碼(9.15m)的圓弧。
  10. 角球區,以4個角為圓心,半徑為 1m的 1/4 圓弧。

??現代足球運動起源于英國,當時英制的長度單位是“碼”,1碼等于0.9144米,約0.915米。 那么,英制長度10碼換算成公制長度就是9.15米。 這就是9.15米的來源。

二、邊線和底線

以世界杯比賽場地為例,長度115碼(105m),寬度74碼(68m)。

??2022世界杯決賽將在盧賽爾球場舉行,它由中國鐵建國際集團承建。

假設 HTML結構如下,這里用到的標簽僅僅只有一個。

<filed></filed>

為了尺寸計算方便,采用em相對單位進行換算,數值就可以采用真實的“碼”,好處是都是整數,簡單繪制一下外圍邊線和底線,如下:

filed{
font-size: 5px;
width: 115em; /*表示115碼*/
height: 74em;
border: 5em solid transparent;
outline: 2px solid #fff;/*線寬就用固定值*/
outline-offset: -5em;
background: #43A63C;
}

注意這里實現的小細節:這里外層的線框是通過outline實現的,還預留了一個5em的透明邊框,這是因為背景的位置和尺寸百分比計算是根據內容區域的,并不包含邊框。比如,background-postion:0 0表示的就是線框內的左上點,background-postion: 100% 100%表示的就是線框內的右下點,,background-size: 100%表示的就是線框內最大尺寸,如下:

圖片

透明邊框的好處

還有一個好處,透明邊框仍然是可以繪制背景的,比如深淺不同的草皮就可以繪制在邊框之外,這個后面再說。

準備工作完成了,下面是具體的繪制過程。

三、中線、開球點和中圈

在繪制之前,可以簡單規劃一下,通過 CSS 變量將各部分分離開來,這樣看起來會更加清晰,例如:

filed{
--中線: xxx;
--中圈開球點: xxx;
...
background:
/*越靠前的背景越靠上*/
var(--中線),
var(--中圈開球點),
...,
#43A63C
}

這個技巧在之前這篇文章中有相關介紹:??由 transform 被占用引發的思考????

首先是中線,使用線性漸變linear-gradient。

--中線: linear-gradient(#fff, #fff) center/2px 100% no-repeat;

可能有些同學還不太清楚上面這一段 background的簡寫,可以看下面這張圖(下面只列舉了常用的,實際上還有更多屬性)。

圖片

背景的簡寫

效果如下:

圖片

中線

然后是開球點和中圈。

??球在開出前,其他隊員不得進入中圈。

這是一個半徑為10碼的圓,可以通過一個徑向漸變radial-gradient實現。

--中圈: radial-gradient( closest-side circle, #fff 2px, transparent 0 calc(100% - 2px), #fff 0 100%, transparent 0) center/20em 20em no-repeat;

注意,這里使用了關鍵詞closest-side,表示最近的邊,可以根據背景尺寸直接控制圓的大小,默認值是farthest-side,其他選項詳細如下:

關鍵字

描述

closest-side

漸變中心距離容器最近的邊作為終止位置。

closest-corner

漸變中心距離容器最近的角作為終止位置。

farthest-side

漸變中心距離容器最遠的邊作為終止位置。

??farthest-corner(默認值)??

漸變中心距離容器最遠的角作為終止位置。

當然,對于完全對稱的容器,closest-* 和 farthest-*是完全相同的,各自的區別如下所示:

圖片

徑向漸變關鍵詞

繪制效果如下:

圖片

中圈

四、罰球區、球門區

罰球區通常也叫大禁區,是一個44碼*18碼的矩形線框。

??守門員在罰球區內可以用手觸球,出去就不行了,還有就是在這個區域犯規,容易被判點球。

線性漸變不像徑向漸變那樣,并不能直接畫出這種矩形線框,我采用的方式是覆蓋的方式,也就是一塊綠色的覆蓋在一塊白色的背景之上,實現如下:

--大禁區: linear-gradient(#43A63C, #43A63C) left center/calc(18em - 2px) calc(44em - 4px) no-repeat, linear-gradient(#fff, #fff) left center/18em 44em no-repeat;

動態演示如下:

圖片

大禁區實現演示

兩邊半場都有罰球區域,而且長的也完全一樣,需要再重新繪制一份一模一樣的嗎?

??????當然不需要!

凡事看到相同或相似的圖案都需要考慮能否避免重復的工作量?

仔細觀察,兩邊的罰球區域正好可以通過水平平鋪repeat-x實現,只需要改變背景大小就行了,示意如下:

圖片

平鋪實現演示

你也可以查看動態演示:

圖片

平鋪實現動態演示

用代碼實現就是:

--大禁區: linear-gradient(to right, #43A63C calc(18em - 2px), transparent 0) 0 center/calc(100% - 18em + 2px) calc(44em - 4px) repeat-x, linear-gradient(to right, #fff 18em, transparent 0) 0 center/calc(100% - 18em) 44em repeat-x;

這樣就能在不增加漸變數量的情況下實現多份相同的背景,效果如下:

圖片

大禁區

然后是球門區,通常叫小禁區,是一個20碼*6碼的矩形線框。

??球門球時,由守方隊員在球門區內任意一點將球放定后踢出。

這個和罰球區繪制方法一致,就不多描述了。

--小禁區: linear-gradient(to right, #43A63C calc(6em - 2px), transparent 0) 0 center/calc(100% - 6em + 2px) calc(20em - 4px) repeat-x, linear-gradient(to right, #fff 6em, transparent 0) 0 center/calc(100% - 6em) 20em repeat-x;

效果如下:

圖片

小禁區

最后是球門。球門在底線后面,由于是俯視圖,只需要知道長度8碼就行了,寬度可以隨便給一個。

??足球要完全越過門線才算進球,僅超過1/2也不行。

這個和上面繪制方法一致,不過需要注意background-position的位置,是負數。

--球門: linear-gradient(to right, #43A63C calc(3em - 4px), transparent 0) calc(-3em + 2px) center/calc(100% + 3em) calc(8em - 4px) repeat-x, linear-gradient(to right, #fff 3em, transparent 0) -3em center/calc(100% + 3em) 8em repeat-x;

這里就體現出前面透明的好處了,可以將背景繪制在邊框上,效果如下:

圖片

球門

這樣就完成了所有矩形線框的繪制。

五、罰球點、罰球弧、角球弧

最后是幾條比較重要的圓弧。

首先是罰球點,又稱點球點,距離球門12碼。

??這個相信很多人都知道,12碼點球主罰的地方就是這里。

這是一個圓點,直接通過一個徑向漸變radial-gradient繪制,這個我們等會再來繪制,先畫下面的。

然后是罰球弧,它是以罰球點為圓心,半徑為10碼的圓弧,和中圈一樣。

??在罰點球時,除守方守門員和主罰隊員外,雙方其他隊員都必須退出罰球區及罰球弧外,因為到罰球點的距離都是 10 碼。

和中圈大小是一樣的,只是位置不同,注意圓心距離左側的距離是12碼,由于左右都是一樣的,可以用前面提到的repeat-x方式實現(當然這里不寫也行,因為默認就是平鋪的),示意如下:

圖片

平鋪實現演示

你也可以查看動態演示:

圖片

平鋪實現動態演示

用代碼實現就是:

--罰球弧: radial-gradient( circle at 12em center, transparent calc(10em - 2px), #fff 0 10em, transparent 0) 0 center/calc(100% - 24em) 100%;

效果如下:

圖片

最上層的罰球弧

現在這個圓弧覆蓋在最上面,由于罰球區是通過覆蓋的方式實現的,所以可以將罰球弧放在罰球區下面,通過改變background的先后順序就可以了,如下:

多背景的情況下,前面的背景層級 > 后面的背景層級。

background: 
/* var(--罰球弧), */
var(--小禁區),
var(--大禁區),
var(--罰球弧), /* 將罰球弧移動到大禁區下面*/
var(--球門),
var(--中線),
var(--中圈),
#43A63C;
}

這樣就正常了。

圖片

罰球弧

然后用同樣的方式把罰球點補上。

--罰球點: radial-gradient( circle at 12em center, #fff 2px, transparent 0) 0 center/calc(100% - 24em) 100%;

效果如下:

圖片

?罰球點

最后是角球弧。位于球場四角,是半徑為1m的 1/4 圓弧。

??用來發角球的地方,守方隊員在己方半場將球自底線處踢出界外,攻方獲得的就是發角球的機會

如果按照一般的思路,肯定是繪制 4 個 1/4 圓弧就行了,不過這里還可以采用另一種方式。仔細想一下,這4個圓弧合在一起是不是剛好就是一個完整的圓?經過位移、平鋪就可以了,思路演示如下

這個思路在之前這篇文章中有用到:??CSS 實現優惠券的技巧??

圖片

1/4圓平鋪原理演示

用代碼實現就是:

--角球弧: radial-gradient( circle at 1em 1em, transparent calc(1em - 2px), #fff 0 1em, transparent 0) -1em -1em/100% 100%;

這樣用一個漸變就同時繪制出了4個圓,效果如下:

圖片

4個完整角球弧

可以看到,4個圓弧已經均勻分布在4個角落了,但是已經超出了線外,這個也非常好解決,默認情況下背景是可以繪制在border-box范圍內的,只需要通過background-clip裁剪到content-box內就行了,如下:

--角球弧: radial-gradient( circle at 1em 1em, transparent calc(1em - 2px), #fff 0 1em, transparent 0) -1em -1em/100% 100% content-box;/*添加裁剪區域*/

這樣就完美了。

圖片

使用background-clip裁剪后的角球弧

六、草坪

到目前位置,球場的所有部分基本已經完成了,最后再鋪上深淺相間的草坪。

??不僅僅是為了好看,還能緩解觀眾和球員的視覺疲勞,同時也方便裁判和球員看清是否越位。

關于草坪的條紋間隔貌似不是很統一?這里就大概給一個數值,用線性漸變即可,如下:

--草坪: linear-gradient(90deg, transparent 50%, rgba(0,0,0,.4) 0% 100%) center/10% 100%;

由于前面罰球區等用到了覆蓋的方式,所以這里不能直接將草坪繪制在最底下,需要繪制在最上層,效果如下:

圖片

直接覆蓋的草坪

可以看到,僅僅通過半透明的覆蓋還是很不自然的,所以需要將顏色混合一下,需要用到background-blend-mode,比較復雜,這里就不展開了,設置如下:

overlay,soft-light,hard-light屬于融合混合模式,比較適合這類情況。

background-blend-mode: soft-light /*柔光*/

效果如下:

圖片

混合模式

有點奇怪...原因是上面設置的是所有圖層的background-blend-mode,我們其實只需要設置最頂層的草坪,那怎么處理呢?我起初以為background縮寫是包含background-blend-mode的,這樣的話可以單獨給某一層設置了,可惜這個不支持(我猜測這個屬性出現的稍晚一些,沒有統一到背景里)。

沒辦法,只能逐層設置了,第1層設置 soft-light,剩下的全部都是normal,如下:

background-blend-mode: soft-light, normal,...,normal;

后面的normal可以多,但是不能少,原因在于,會根據背景數量自動補充,如果數量不足,會重新開頭循環(這個補充規則其實跟其他背景屬性,例如 background-size是一樣的)。

圖片

混合模式自動填充規則

這樣就非常自然了,效果如下:

圖片

最終效果

下面是完整代碼(其實沒多少行):

filed{
font-size: 5px;
width: 115em;
height: 74em;
--中線: linear-gradient(#fff, #fff) center/2px 100% no-repeat;
--中圈: radial-gradient( closest-side circle, #fff 2px, transparent 0 calc(100% - 2px), #fff 0 100%, transparent 0) center/20em 20em no-repeat;
--大禁區: linear-gradient(to right, #43A63C calc(18em - 2px), transparent 0) 0 center/calc(100% - 18em + 2px) calc(44em - 4px) repeat-x, linear-gradient(to right, #fff 18em, transparent 0) 0 center/calc(100% - 18em) 44em repeat-x;
--小禁區: linear-gradient(to right, #43A63C calc(6em - 2px), transparent 0) 0 center/calc(100% - 6em + 2px) calc(20em - 4px) repeat-x, linear-gradient(to right, #fff 6em, transparent 0) 0 center/calc(100% - 6em) 20em repeat-x;
--球門: linear-gradient(to right, #43A63C calc(3em - 4px), transparent 0) calc(-3em + 2px) center/calc(100% + 3em) calc(8em - 4px) repeat-x, linear-gradient(to right, #fff 3em, transparent 0) -3em center/calc(100% + 3em) 8em repeat-x;
--罰球弧: radial-gradient( circle at 12em center, transparent calc(10em - 2px), #fff 0 10em, transparent 0) 0 center/calc(100% - 24em) 100%;
--罰球點: radial-gradient( circle at 12em center, #fff 2px, transparent 0) 0 center/calc(100% - 24em) 100%;
--角球弧: radial-gradient( circle at 1em 1em, transparent calc(1em - 2px), #fff 0 1em, transparent 0) -1em -1em/100% 100% content-box;
--草坪: linear-gradient(90deg, transparent 50%, rgba(0,0,0,.5) 0% 100%) center/10% 100%;
background:
var(--草坪),
var(--角球弧),
var(--罰球點),
var(--球門),
var(--小禁區),
var(--大禁區),
var(--罰球弧),
var(--中線),
var(--中圈),
#43A63C;
background-blend-mode: soft-light, normal, normal, normal, normal, normal, normal, normal, normal, normal, normal, normal;
border: 5em solid transparent;
outline: 2px solid #fff;
outline-offset: -5em;
}

你也可以訪問以下任意鏈接:

  • CSS football filed - 碼上掘金 (juejin.cn)[1]
  • CSS football filed (codepen.io)[2]
  • CSS football filed (runjs.work)[3]

七、總結一下

漸變是 CSS 中非常強大但比較繁瑣的功能了,幾乎是萬能的,能夠設計出來的都可以通過漸變繪制出來,只是實現的復雜度問題,擅于發現圖形的規律也能有效地減少漸變的復雜度,下面簡單總結一下。

  1. 背景的位置和尺寸的百分比計算是根據內容區域的,并不包含邊框。
  2. 透明邊框仍然是可以繪制背景的。
  3. 通過 CSS 變量將背景各部分分離開來,這樣看起來會更加清晰。
  4. 線性漸變不像徑向漸變那樣,并不能直接畫出這種矩形線框,可以用兩層漸變覆蓋的方式實現。
  5. 凡事看到相同或相似的圖案都可以考慮使用背景平鋪來減少工作量。
  6. 多背景的情況下,前面的背景層級 > 后面的背景層級。
  7. 4 個 1/4圓可以通過一個完整的圓位移平鋪實現。
  8. 默認情況下背景是可以繪制在邊框范圍內的,可以通過background-clip改變繪制范圍。
  9. 背景混合模式并不在background簡寫屬性中,需要單獨書寫,可以讓圖層混合更加自然。
  10. 背景混合模式會根據背景數量自動補充,如果數量不足,會重新開頭循環。

當然實際工作中肯定是不推薦的,更多是學習掌握漸變相關知識,這樣繪制一些活動小圖標,或者在某些不方便改變 HTML 結構時可以有更多的思路和方案,不是嗎?

參考資料

[1]CSS football filed - 碼上掘金 (juejin.cn): ??https://code.juejin.cn/pen/7172148336886022175。??

[2]CSS football filed (codepen.io): ??https://codepen.io/xboxyan/pen/BaVqogP。??

[3]CSS football filed (runjs.work): ??https://runjs.work/projects/8f18caa4fb1248dc。??

責任編輯:姜華 來源: 前端偵探
相關推薦

2012-09-27 18:04:53

NEC巴西足球場館ICT

2025-05-13 00:00:05

2017-03-15 18:43:46

華為

2024-03-06 11:16:10

2023-03-22 09:00:38

2024-12-09 09:25:30

2023-05-08 09:08:33

CSS前端

2010-09-30 10:13:55

超算HPC

2023-07-17 09:19:20

CSSCSS 漸變

2009-11-06 09:44:11

Apache

2016-11-24 12:07:42

Android萬能圓角ImageView

2020-12-23 11:14:49

人工智能銷售行業AI

2022-06-27 08:36:08

PythonLambda

2014-02-17 10:56:21

Hadoop

2022-11-30 13:13:41

節能減碳PUE

2011-06-16 15:57:25

Android

2009-12-03 18:13:36

PHP萬能密碼

2020-06-16 08:32:00

人工智能技術機器學習

2022-11-21 09:57:18

網關系統
點贊
收藏

51CTO技術棧公眾號

主站蜘蛛池模板: 九九色综合 | 日韩在线中文字幕 | 亚洲欧美在线一区 | 欧美中文在线 | 请别相信他免费喜剧电影在线观看 | 亚洲精品一区二区网址 | 亚洲精品视频免费观看 | 伊人伊人伊人 | 色约约视频 | 日韩在线欧美 | 精品欧美一区二区三区久久久小说 | 亚洲成人免费 | 久久久久久九九九九九九 | 国产乱肥老妇国产一区二 | 中文字幕色站 | 亚洲视频在线播放 | www.夜夜骑.com | 中文字幕不卡视频在线观看 | 精品美女视频在线观看免费软件 | 91久久国产综合久久91精品网站 | 欧美日韩亚洲系列 | 欧美精品在线免费观看 | 蜜桃av一区二区三区 | 久久五月婷| 国产一级视频在线播放 | 91久久国产综合久久 | 人人干人人干人人干 | 91免费入口 | 国产亚洲成av人在线观看导航 | 天天干天天操 | 91国产在线播放 | 黑人精品xxx一区一二区 | 天天操天天干天天爽 | 国产精品激情在线 | 亚洲男女激情 | 欧美日韩中文在线 | 一区二区三区高清在线观看 | 找个黄色片 | 成人 在线 | 日本午夜免费福利视频 | 一二三四av |