Levix

Levix's zone

x
telegram

CSS 遮罩 - CSS Masking

原文鏈接:https://ishadeed.com/article/css-masking/

在設計世界中,遮罩(masking)是實現獨特設計效果的流行技術,作為一名設計師,我已經使用過很多次,但我在網頁上使用 CSS 遮罩的次數很少,我認為我不使用 CSS 遮罩的原因是瀏覽器支持情況,它們在 blink 瀏覽器(Chrome 和 Edge)中只支持了部分特性,而在 Safari 和 Firefox 中完全支持。

好消息是 CSS 遮罩將成為 Interop 2023 的一部分,這意味著我們應該期待跨瀏覽器支持(耶!!)。

在這篇文章中,我將介紹 CSS 遮罩是什麼,它是如何工作的,以及輸出一些結合它的用例和示例。

讓我們開始吧。

什麼是遮罩?#

簡單地說,遮罩的工作方式是在不擦除元素的情況下將其部分隱藏。

參考以下圖片:

https://p3-juejin.byteimg.com/tos-cn-i-k3u1fbpfcp/eeb44a70603e4ebb925dab0869a72ea7~tplv-k3u1fbpfcp-zoom-1.image

我們有一張圖片和一個遮罩,在像 Photoshop 這樣的設計應用程序中,我們可以把圖片插入到灰色形狀內,這樣就會產生一個蒙版的圖像。

它的工作原理是隱藏圖像的某些部分而不是擦除它(它們仍然在那裡,只是被隱藏了)。

image

這就是遮罩的核心概念,使用一個形狀來顯示和隱藏元素的某部分,我們可以進一步探索更獨特的遮罩內容。

例如,我們可以創建一個如下圖那樣的漸變遮罩。

https://p3-juejin.byteimg.com/tos-cn-i-k3u1fbpfcp/a641d661248f4f41a73a0c4383b785c1~tplv-k3u1fbpfcp-zoom-1.image

在漸變中,有填充和透明像素,填充的部分是元素的一部分可見區域,透明的部分則是隱藏的部分。

image

在 Photoshop 中,我們可以向一組圖層添加圖層蒙版,該組內的內容將被遮罩。它的工作原理是使用畫筆工具隱藏組的一部分從而實現遮罩。

image

被遮罩的內容並沒有被擦除,而是被隱藏了(請注意組項目)。

好了,以上都偏理論,在接下來的文章中,我將介紹 CSS 遮罩的使用方式,它是如何工作的以及一些用例和示例。

如何在 CSS 中使用遮罩#

在 CSS 中,有幾種遮罩元素的方式:

  • mask 屬性
  • clip-path 屬性
  • SVG <mask>

mask 屬性和 clip-path 的主要區別在於前者用於圖像和漸變,而後者用於路徑,本文的重點將放在 mask 屬性上。

在 CSS 中,我們有 mask 簡寫屬性,類似於 background 屬性一樣,是的,你沒看錯。這就是我認為它容易記住語法的原因,因為它的語法與 background 屬性完全相同,但具有少量其他屬性。

而不是列出所有的 CSS 遮罩屬性,我將逐步添加一個遮罩功能的示例,讓你可以在視覺上發現差異。

CSS 背景如下所示:

.card__thumb {
    background-image: url('hero-cool.png');
}

CSS 遮罩如下所示:

.card__thumb {
    mask-image: url('hero-cool.png');
}

https://p3-juejin.byteimg.com/tos-cn-i-k3u1fbpfcp/7ad1e12dcd0b41759bce5edb160ea5ba~tplv-k3u1fbpfcp-zoom-1.image

很酷,對吧?這讓你理解和掌握 CSS 遮罩變得更加容易。

現在,讓我們用 CSS 重新做一下最初的示例。

首先,我需要將形狀導出為 png 圖像。

https://p3-juejin.byteimg.com/tos-cn-i-k3u1fbpfcp/37895d18f5fd462ab7f15b9c2fcde9c7~tplv-k3u1fbpfcp-zoom-1.image

假設我想將遮罩應用於該圖像。

<img src="ahmad-shadeed-web-directions.jpg" alt="" />
img {
    mask-image: url("shape.png");
}

你能預測出結果嗎?默認情況下,遮罩會重複,其大小將等於遮罩圖像本身,如下圖所示:

https://p3-juejin.byteimg.com/tos-cn-i-k3u1fbpfcp/dfffd42b05e74891a90c3f25f3eeaaae~tplv-k3u1fbpfcp-zoom-1.image

為了恢復,我們需要將 mask-repeat 設置為 no-repeat,就像 CSS 背景圖像一樣。

img {
    mask-image: url("shape.png");
    mask-repeat: no-repeat;
}

https://p3-juejin.byteimg.com/tos-cn-i-k3u1fbpfcp/5ee977ebbb714383a2831c21f320580c~tplv-k3u1fbpfcp-zoom-1.image

太棒了!請注意,遮罩位於左上角,可以通過 mask-position 更改它,再次注意,語法與 CSS 背景圖片配置完全相同!

img {
    mask-image: url("shape.png");
    mask-repeat: no-repeat;
    mask-position: center;
}

https://p3-juejin.byteimg.com/tos-cn-i-k3u1fbpfcp/e3aa31aaa8ad4fc4880c16ad786f32c2~tplv-k3u1fbpfcp-zoom-1.image

除了位置,我們還可以更改遮罩大小,這對於使用遮罩圖像響應元素的大小很有用。

img {
    mask-image: url("shape.png");
    mask-repeat: no-repeat;
    mask-position: center;
    mask-size: 60%;
}

image

還有一些遮罩屬性,但我現在不想用它們來打擊你學習的興趣,稍後我將用實際用例來介紹它們。

使用 CSS 漸變進行遮罩#

CSS 遮罩不僅僅是使用圖像,我們還可以利用漸變來創建強大且有用的遮罩效果。

稍後我將展示一些有用的用例,但現在,我想重點介紹漸變如何與遮罩配合使用的基本原理。

在以下示例中,mask-image 由從全黑到透明的 CSS 線性漸變組成。

img {
    mask-image: linear-gradient(#000, transparent);
}

image

根據 MDN 的說法:

默認情況下,這意味著遮罩圖像的 alpha 通道將乘以元素的 alpha 通道,可以使用 mask-mode 屬性來控制。

這意味著,你可以使用除黑色以外的任何顏色,遮罩仍將起作用,因為默認遮罩模式設置為 alpha(稍後我將詳細介紹此內容)。

img {
    mask-image: linear-gradient(red, transparent);
}

image

同樣,遮罩的概念是透明像素將被隱藏,以下是具有硬色停止的漸變的簡化示例:

img {
    mask-image: linear-gradient(#000 50%, transparent 0);
}

image

太酷了!現在,核心遮罩概念已經清晰了(我希望如此),讓我們探索一些實際用例的 CSS 遮罩。

實際使用案例和示例#

淡化圖像#

使用遮罩的一個有趣用途是使圖像淡出並與其下面的背景混合。

考慮以下圖像:

css-masking-use-case-fade-image-light.png

乍一看,你可能會想要添加一個與背景顏色相同的漸變。像這樣:

.hero__thumb:after {
    position: absolute;
    inset: 0;
    background: linear-gradient(to top, #f1f1f1, transparent)
}

雖然這可能會起作用,但當主背景顏色改變時,它就會失敗,注意到首頁橫幅會出現頓挫感:

image

使用 CSS 遮罩,我們可以遮蓋首頁橫幅,使其與任何背景顏色配合使用。

.hero__thumb {
    mask-image: linear-gradient(#000, transparent);
}

就這樣!現在淡化過渡效果是真實的,並且不會在更改主頁面背景時失效,請參見以下示例:

https://p3-juejin.byteimg.com/tos-cn-i-k3u1fbpfcp/7b134dee8bca4b839d927dad17813c5b~tplv-k3u1fbpfcp-zoom-1.image

遮罩文本內容:示例 1#

當我們想要顯示長文本但空間不足以完全顯示時,解決方案是在開頭和結尾處淡化文本,然後,文本將在任一方向上動畫以顯示剩餘內容。

考慮以下圖像:

https://p3-juejin.byteimg.com/tos-cn-i-k3u1fbpfcp/3fb3cc8f15ad4464a7c7438a3228a72a~tplv-k3u1fbpfcp-zoom-1.image

再次,使用漸變的 hack 不起作用,因為內容下面的背景被更改了,它可以是純色或圖像。

image

要在 CSS 中實現它,我們需要添加一個漸變遮罩,以在開頭和結尾處淡化內容。

我喜歡在 CSS 漸變中做到這一點並查看結果,然後將其應用為遮罩,這有助於在使用其作為遮罩之前將漸變可視化。

.c-card__footer {
    background-image: linear-gradient(90deg, transparent, #000 15%, #000 85%, transparent 100%);
}

https://p3-juejin.byteimg.com/tos-cn-i-k3u1fbpfcp/d098ef27933847d9aa0060ae8ad7fbb2~tplv-k3u1fbpfcp-zoom-1.image

有了上面的內容,我們就可以將其應用為遮罩。

.c-card__footer {
    mask-image: linear-gradient(90deg, transparent, #000 15%, #000 85%, transparent 100%);
}

還不完美?我們可以微調漸變值,直到結果完美為止。

遮罩文本內容:示例 2#

這與前面的示例相同,但應用於垂直方向,我在 Instagram 的直播視頻中看到過這種情況。

考慮以下圖像:

https://p3-juejin.byteimg.com/tos-cn-i-k3u1fbpfcp/e430dce52b4e45809ac307323f2d5a16~tplv-k3u1fbpfcp-zoom-1.image

請注意,內容從頂部被沖洗出來?這個小地方可以有供稿評論,操作和其他內容。使用 CSS 遮罩非常適合這樣做。

首先,讓我們看一下漸變。

https://p3-juejin.byteimg.com/tos-cn-i-k3u1fbpfcp/6b61045352c6478ca4c241fcd2340887~tplv-k3u1fbpfcp-zoom-1.image

在 CSS 中,它可能是這樣的:

.whatever-the-class-name {
    mask-image: linear-gradient(to bottom, transparent, #000);
}

遮罩列表#

我在研究 CSS 遮罩時看到了這個很酷的例子,這個想法是我們有一系列特徵、課程或其他任何東西,我們想淡化文本來使用戶對其中的內容更加好奇。

考慮以下示例:

https://p3-juejin.byteimg.com/tos-cn-i-k3u1fbpfcp/49cd372a6e0949d4be4f7c4a6625960d~tplv-k3u1fbpfcp-zoom-1.image

你可以在左邊看到一個列表,在最底部淡化,使用 CSS 遮罩非常適合此操作,因為它可以與下面的背景混合,無論是圖像還是深色背景。

image

讓我們看看遮罩漸變,了解其工作原理。

https://p3-juejin.byteimg.com/tos-cn-i-k3u1fbpfcp/766121f339d74105b00f1ad3092e02d9~tplv-k3u1fbpfcp-zoom-1.image

在 CSS 中,它看起來像這樣:

.list {
    mask-image: linear-gradient(to bottom, #000, transparent 95%);
}

有趣的圖像效果#

使用 CSS 遮罩和漸變,創建視覺效果的可能性是無限的。這是一個簡單的示例,說明我們如何為圖像創建視覺效果。

這是我為此演示製作的快速設計。

image

你看到的圖像效果包括 5 個線性漸變,通過為每個漸變添加不同的漸變位置,我們可以獲得類似的效果。

讓我們更詳細地看看漸變:

.thumb {
    mask-image: linear-gradient(to bottom, #000, #000),
    linear-gradient(to bottom, #000, #000),
    linear-gradient(to bottom, #000, #000),
    linear-gradient(to bottom, #000, #000),
    linear-gradient(to bottom, #000, #000);
    mask-size: 18% 70%;
    mask-position: 0 100%, 25% 25%, 50% 50%, 75% 0, 100% 50%;
    mask-repeat: no-repeat;
}

從視覺上看,遮罩如下所示:

image

要在每個矩形的遮罩上創建淡出效果,我們需要更新每個漸變並包括 “transparent” 關鍵字。

.thumb {
    mask-image: linear-gradient(to bottom, transparent, #000),
    linear-gradient(to bottom, #000, transparent),
    linear-gradient(to bottom, transparent, #000),
    linear-gradient(to bottom, #000, transparent),
    linear-gradient(to bottom, transparent, #000);
    mask-size: 18% 70%;
    mask-position: 0 100%, 25% 25%, 50% 50%, 75% 0, 100% 50%;
    mask-repeat: no-repeat;
}

image

我們還可以在懸停時對遮罩大小或位置進行動畫處理。

css-mask-image-effect.mp4

這很強大,想像一下,將其與基於滾動的動畫結合起來,事情可能會失去控制(不過是以一種好的方式)。

圓角標籤頁#

我考慮為 UI 特效嘗試 CSS mask,這個特效叫做 圓角標籤頁

這個想法是我們希望以一種與元素的 border-radius 融合的方式將元素的側面圓角化。

https://p3-juejin.byteimg.com/tos-cn-i-k3u1fbpfcp/259a4b1c180743168feaf25e855022ab~tplv-k3u1fbpfcp-zoom-1.image

在這篇博客文章中,Chris Coyier 解釋了一種使用多個伪元素實現的技巧,更動態的解決方案是使用 CSS mask。

首先,讓我們更仔細地看一下我想要實現的形狀。

https://p3-juejin.byteimg.com/tos-cn-i-k3u1fbpfcp/3d51e7bdf9024e9392e7f4daebcccc10~tplv-k3u1fbpfcp-zoom-1.image

形狀由一個正方形和一個圓形組成,我們需要的是它們的交集。

如何實現呢?我們可以使用多層 mask 以及 mask-composite 屬性在它們上面執行 composting 操作。

首先,我們需要創建一個元素來容納 mask。

.nav-item.active:before {
    content: "";
    position: absolute;
    left: 100%;
    bottom: 0;
    width: 24px;
    height: 24px;
    background-color: var(--active-bg);
}

https://p3-juejin.byteimg.com/tos-cn-i-k3u1fbpfcp/50781a08b2d64b2ead3f7dba3feaed74~tplv-k3u1fbpfcp-zoom-1.image

在這個空間中,我們需要繪製一個圓和一個正方形以進行組合,幸運的是,我們可以通過混合線性和徑向漸變來實現。

.nav-item.active:before {
    content: "";
    position: absolute;
    left: 100%;
    bottom: 0;
    width: 24px;
    height: 24px;
    background-color: var(--active-bg);
    background-image: linear-gradient(to top, #000, #000),
    radial-gradient(circle 15px at center, #000 80%, transparent 81%);
    background-size: 12px 12px, 100%;
    background-position: bottom left, center;
    background-repeat: no-repeat, repeat;
}

注意以下幾點:

  • 我為正方形添加了 12px 12px 作為大小。
  • 正方形位於左下角。
  • 正方形形狀不需要重複。

https://p3-juejin.byteimg.com/tos-cn-i-k3u1fbpfcp/4721c2f91ce64fcfa61fbb57fa1f5882~tplv-k3u1fbpfcp-zoom-1.image

上面只是為了視覺上說明兩個漸變的效果,下一步是實現它們!在 CSS 遮罩中,我們可以使用 mask-composite 屬性來組合兩個形狀。

.nav-item.active:before {
    content: "";
    position: absolute;
    left: 100%;
    bottom: 0;
    width: 24px;
    height: 24px;
    background-color: var(--active-bg);
    mask-image: linear-gradient(to top, red, red),
    radial-gradient(circle 15px at center, green 80%, transparent 81%);
    mask-size: 12px 12px, 100%;
    mask-position: bottom left, center;
    mask-repeat: no-repeat, repeat;
    mask-composite: subtract;
}

這是上述形狀的 CSS 右側。對於另一個,我們只需更改 mask-position 即可翻轉。

.nav-item.active:after {
    /* 其他樣式 */
    mask-position: bottom right, center;
}

演示

多個頭像裁剪#

在我關於鏤空效果的文章中,我探討了使用 CSS 創建鏤空的不同方法。

其中一個例子非常適合 CSS 遮罩。

使用 CSS 遮罩,我們可以使用徑向漸變來實現該效果。

.avatar {
    -webkit-mask-image: radial-gradient(ellipse 54px 135px at 11px center, #0000 30px, #000 0);
}

我強烈建議閱讀這篇文章,因為有很多像這樣的詳細例子。

結論#

當我開始學習 CSS 遮罩時,資源有限,更重要的是,我們可以在日常工作流程中使用的實際用例非常少。我希望通過本文讓你知道在下一個項目中在哪裡可以使用 CSS 遮罩。

順便說一句,我沒有深入研究 mask-mode 等屬性,因為說實話,我沒有發現用它們來解決的問題(直到現在)。當我有一個更有說服力的使用這種屬性的例子時,我會更新這篇文章。

更多資源#

如果您想在更多的 CSS 遮罩示例中提高自己的技能,那麼您必須查看以下內容:

感謝您的閱讀。

載入中......
此文章數據所有權由區塊鏈加密技術和智能合約保障僅歸創作者所有。