IconCard 📦
以「SF Symbol 為前景,透明方紙為背景」的元件,適合用於當遮罩或反面遮罩。
下圖顯示 img
(IconCard) 從套用 .foregroundColor(.black)、.background(Color.white)、.compositingGroup()、.luminanceToAlpha(),一直到 paper
(紅色星點紙) 套用 .mask() 的整個過程。
這個過程後來被濃縮成一個 View extension:.inverseMask() 🌀

import SwiftUI
import Workaround // for `SystemImage`
/// # 📦 IconCard
/// - icon: SF Symbol 名稱。
/// - size: ⚠️ 注意:這是圖示大小,不是整張卡的大小‼️
/// ## Example
/// ````
/// IconCard(icon: "heart.fill", size: 32)
/// ````
public struct IconCard: View {
// properties
let iconSize: CGFloat // icon size
let icon : String // icon name
/// public init
public init(_ icon: String, size: CGFloat = 32) {
self.icon = icon
self.iconSize = size
}
// body
public var body: some View {
// 1. 選用 ZStack,讓物件可以在上下層間輕鬆堆疊。
// ⭐️ 先不限制 ZStack 的大小,它的大小由外部環境決定。
ZStack {
// 2. 先準備一張「透明紙」:這裡有兩個用意 ⭐️
// 1. 用 Rectangle 來定義此「元件的大小」(否則會以下面的 SystemImage 為準)。
// 2. 先指定 fg = .clear,將來如果整個元件再被設定 .foreground() 時,
// - Rectangle 的 fg 還是 .clear (不會被 overridden‼️)
// - SystemImage 的 fg 因為還沒被設定過,所以就可以被改寫。
Rectangle()
.foregroundColor(.clear) // ⭐️ 指定「透明色」!
// 3. 然後在上面畫圖示,並設定圖示大小。
// ⭐️ 注意:雖然沒有指定前景色,但在深色模式下,會用「白色」表示。
SystemImage(icon)
.frame(width: iconSize, height: iconSize)
} // container (ZStack)
} // body
}
Last updated
Was this helpful?