View — Button

在 SwiftUI 中,可以通过自定义 ButtonStyleModifier 来实现对按钮样式的批量设置。这使得你可以复用样式规则,避免重复代码,并提供更灵活的样式管理方式。

下面是一些常见的方法,详细说明如何为 Button 批量设置样式。


方法 1:使用自定义 ButtonStyle #

SwiftUI 提供了 ButtonStyle 协议,可以创建复用的样式规则,适用于多个按钮。

示例代码:自定义的按钮样式 #

import SwiftUI

struct CustomButtonStyle: ButtonStyle {
    func makeBody(configuration: Configuration) -> some View {
        configuration.label
            .padding()
            .foregroundColor(.white)
            .background(configuration.isPressed ? Color.blue.opacity(0.6) : Color.blue)
            .cornerRadius(10)
            .scaleEffect(configuration.isPressed ? 0.95 : 1.0) // 点击效果
            .animation(.easeInOut(duration: 0.2), value: configuration.isPressed)
    }
}

struct CustomButtonStyleExample: View {
    var body: some View {
        VStack(spacing: 20) {
            Button("Button 1") {
                print("Button 1 tapped")
            }
            
            Button("Button 2") {
                print("Button 2 tapped")
            }
            
            Button("Button 3") {
                print("Button 3 tapped")
            }
        }
        .buttonStyle(CustomButtonStyle()) // 批量应用样式
    }
}

效果 #

  1. 所有按钮使用自定义颜色、圆角、点击动画等样式。
  2. 使用 .buttonStyle(CustomButtonStyle()) 一次性应用到所有按钮。

方法 2:使用 ViewModifier 方式 #

ViewModifier 是 SwiftUI 中另一个常见的样式复用机制,用于对视图(包括 Button)定义样式。

示例代码:自定义 ViewModifier #

import SwiftUI

struct ButtonModifier: ViewModifier {
    func body(content: Content) -> some View {
        content
            .padding()
            .foregroundColor(.white)
            .background(Color.green)
            .cornerRadius(8)
    }
}

extension View {
    func customButtonStyle() -> some View {
        self.modifier(ButtonModifier())
    }
}

struct ButtonModifierExample: View {
    var body: some View {
        VStack(spacing: 20) {
            Button("Button 1") {
                print("Button 1 tapped")
            }
            .customButtonStyle() // 使用自定义 Modifier
            
            Button("Button 2") {
                print("Button 2 tapped")
            }
            .customButtonStyle() // 使用自定义 Modifier
            
            Button("Button 3") {
                print("Button 3 tapped")
            }
            .customButtonStyle() // 使用自定义 Modifier
        }
    }
}

效果 #

  1. .buttonStyle() 类似,但更加灵活,可以扩展到任意视图。
  2. 通过 modifier 的方式单独为每个按钮应用样式。

方法 3:批量应用样式到整个 Button #

如果按钮样式需要统一,可以通过 EnvironmentGroup 针对多个按钮集中设置样式。

示例代码:使用 Group for 批量样式 #

import SwiftUI

struct GroupButtonStyleExample: View {
    var body: some View {
        VStack(spacing: 20) {
            Group {
                Button("Button 1") {
                    print("Button 1 tapped")
                }
                Button("Button 2") {
                    print("Button 2 tapped")
                }
                Button("Button 3") {
                    print("Button 3 tapped")
                }
            }
            .buttonStyle(DefaultCustomStyle())
        }
    }
}

struct DefaultCustomStyle: ButtonStyle {
    func makeBody(configuration: Configuration) -> some View {
        configuration.label
            .padding()
            .frame(maxWidth: .infinity)
            .foregroundColor(.white)
            .background(Color.orange)
            .cornerRadius(12)
            .opacity(configuration.isPressed ? 0.8 : 1.0) // 点击效果
    }
}

效果 #

  1. 将多个 Button 包裹在一个 Group 中,避免逐个手动设置。
  2. Group 中的所有按钮会自动应用 .buttonStyle(DefaultCustomStyle()) 样式规则。

方法 4:直接设置容器中的自定义样式 #

如果按钮分布在页面各处,你可以使用 SwiftUI 的环境设置,由 .environment().buttonStyle() 来统一样式。

使用 .buttonStyle() 统一全局按钮样式 #

import SwiftUI

struct EnvironmentButtonStyleExample: View {
    var body: some View {
        VStack {
            Text("Global Button Style")
                .font(.headline)
            
            // 全局作用的 button 样式
            VStack(spacing: 20) {
                Button("Button 1") {}
                Button("Button 2") {}
                Button("Button 3") {}
            }
            .buttonStyle(DefaultCustomStyle()) // 全局应用样式
        }
    }
}

struct DefaultCustomStyle: ButtonStyle {
    func makeBody(configuration: Configuration) -> some View {
        configuration.label
            .padding()
            .background(Color.purple)
            .foregroundColor(.white)
            .cornerRadius(8)
            .font(.headline)
            .shadow(color: .purple.opacity(0.5), radius: 5, x: 0, y: 3)
    }
}

效果 #

  1. 在一个特定的 View 范围内,所有按钮都会自动使用定义的样式。
  2. 不需要为每个按钮单独指定样式。

方法 5:动态样式(通过状态设置按钮样式) #

通过状态(如点击、禁用等)动态更改按钮样式,可以达到动态效果的批量管理。

示例代码:动态按钮状态样式 #

import SwiftUI

struct DynamicButtonStyle: ButtonStyle {
    var isEnabled: Bool
    
    func makeBody(configuration: Configuration) -> some View {
        configuration.label
            .padding()
            .foregroundColor(isEnabled ? .white : .gray)
            .background(isEnabled ? Color.blue : Color.gray)
            .cornerRadius(10)
            .opacity(configuration.isPressed && isEnabled ? 0.8 : 1.0)
            .animation(.easeInOut(duration: 0.2), value: isEnabled)
    }
}

struct DynamicButtonExample: View {
    @State private var isButtonEnabled = true
    
    var body: some View {
        VStack(spacing: 20) {
            Button("Tap Me") {
                print("Button tapped!")
            }
            .buttonStyle(DynamicButtonStyle(isEnabled: isButtonEnabled)) // 动态样式
            
            Toggle("Enable Button", isOn: $isButtonEnabled)
                .padding()
        }
    }
}

效果 #

  1. 按钮样式根据 isEnabled 状态动态调整:
    • 如果按钮启用,背景为 蓝色,并可交互。
    • 如果禁用(isEnabled = false),样式变为 灰色,不可交互。
  2. 遵循动态样式逻辑是一种更灵活的管理方式。

总结 #

根据需求和使用场景,可以选择以下方法来批量设置 Button 样式:

方法适用场景
方法 1:自定义 ButtonStyle最推荐的方案,全局一致,且专为 Button 提供设计。
方法 2:自定义 Modifier适合用于按钮和其他视图混合使用的场景,扩展性更强,但需要手动应用 Modifier。
方法 3:Group 样式设置多个按钮集中在一个容器时最方便,可以批量应用 .buttonStyle()
方法 4:全局环境应用样式对整个页面或范围的按钮设置一致样式,但不适合局部按钮的样式差异场景。
方法 5:动态样式适合需要根据状态(如启用、禁用、按下等)动态调整按钮外观的场景。
本文共 1306 字,上次修改于 Jan 23, 2025