NeuCard 📦

看起來會浮現在平面上的圓角卡片設計,卡片上有一個圖示,下方有一個靠左的文字標題,卡片邊緣還用漸層的方式描繪,非常特別。

import SwiftUI

public struct NeuCard: View, Identifiable {
    
    public let id = UUID()
    var title   : String   // 卡片標題
    var iconName: String   // 卡片圖示 (SF Symbol)
    
    // init
    public init(title: String, icon: String) {
        self.title    = title
        self.iconName = icon
    }
    
    // view body
    public var body: some View {
        
        // card icon
        let icon = Image(systemName: iconName)
            .resizable()                       // ⭐️ 讓圖放大到跟「彩紙」一樣大
            .scaledToFit()                     // ⭐️ = .aspectRatio(contentMode: .fit)
        
        // border
        let roundedRect = RoundedRectangle(cornerRadius: 15)
        let border = roundedRect
            .stroke(Neu.cardRim, lineWidth: 2)  // ⭐️ 使用「漸層」畫線
        
        // container
        return VStack {
            
            // 1. 卡片圖示
            Neu.cardIcon           // ⭐️ 將漸層視為一張「彩紙」
                .mask(icon)        // ⭐️ 將 icon 的形狀「剪下來」
                .frame(width: 100, height: 140)
                .padding(40)
                // ⭐️ 注意:雖然 icon 在 mask 裡面,但還是會影響到。
                .font(.system(size: 150, weight: .thin))  // ⭐️ 讓圖的「線條變細」
                
                // ⭐️ 西北打「亮面」(highlight)、東南打「陰影」,
                //    可以讓整個圖具有「突出」的立體感!
                .shadow(color: .white, radius: 2, x: -3, y: -3)             // highlight
                .shadow(color: Neu.color.iconShadow, radius: 2, x: 3, y: 3) // shadow
            
            // 2. 卡片文字
            HStack {
                Text(title)
                    .foregroundColor(Neu.color.text)
                    .bold()
                    .padding(.leading)
                    .padding(.bottom)
                Spacer()
            }
            
        } // container (VStack)
            .background(Neu.color.cardBackground)  // 卡片背景色
            .clipShape(roundedRect)                // ⭐️ 剪圓角。也可用 .cornerRadius()
            .frame(width: 180)                     // 限制寬度 = 180
            
            // ⭐️ 製造「突出的立體感」,設定的數值越大,浮出的感覺越高!
            .shadow(color: Color.white.opacity(0.9), radius: 18, x: -18, y: -18)
            .shadow(color: Neu.color.iconShadow.opacity(0.5), radius: 14, x: 14, y: 14)
            
            // ⭐️ 畫「漸層邊線」
            .overlay(border)
    }
}

Last updated