sheet的基本用法

在 SwiftUI 中,.sheet 是一个 视图修饰符(View Modifier) ,用于模态呈现(Modal Presentation)一个新的视图(通常是从底部滑出的卡片式界面)。它类似于 UIKit 中的 present(_:animated:completion:)


基本语法

swift 复制代码
.sheet(
    isPresented: Binding<Bool>,  // 控制是否显示
    onDismiss: (() -> Void)? = nil,  // 关闭时的回调
    content: () -> Content  // 要显示的视图
)

参数说明

参数 类型 说明
isPresented Binding<Bool> 控制 sheet 是否显示(true 显示,false 隐藏)
onDismiss (() -> Void)? sheet 关闭时触发的回调(可选)
content () -> Content 返回要显示的视图(闭包)

基本使用示例

1. 显示一个简单 Sheet

swift 复制代码
struct ContentView: View {
    @State private var isShowingSheet = false

    var body: some View {
        Button("Show Sheet") {
            isShowingSheet = true
        }
        .sheet(isPresented: $isShowingSheet) {
            Text("This is a Sheet!")
                .padding()
        }
    }
}

效果 :点击按钮后,从底部弹出 Text("This is a Sheet!")


2. 传递数据并自定义 Sheet 内容

swift 复制代码
struct ContentView: View {
    @State private var isShowingSheet = false
    @State private var userName = ""

    var body: some View {
        VStack {
            TextField("Enter your name", text: $userName)
            Button("Show Greeting Sheet") {
                isShowingSheet = true
            }
        }
        .sheet(isPresented: $isShowingSheet) {
            GreetingView(name: userName)
        }
    }
}

struct GreetingView: View {
    let name: String

    var body: some View {
        VStack {
            Text("Hello, \(name)!")
            Button("Dismiss") {
                // 如何关闭?👉 需要传递 Binding 或使用 @Environment(\.dismiss)
            }
        }
    }
}

问题GreetingView 如何关闭自己?👉 可以使用 @Environment(\.dismiss)


3. 在 Sheet 内部关闭自己(iOS 15+)

swift 复制代码
import SwiftUI

struct GreetingView: View {
    @Environment(\.dismiss) var dismiss  // 获取 dismiss 方法
    let name: String

    var body: some View {
        VStack {
            Text("Hello, \(name)!")
            Button("Dismiss") {
                dismiss()  // 关闭当前 Sheet
            }
        }
    }
}

说明

  • @Environment(\.dismiss) 是 SwiftUI 提供的一个环境变量,用于关闭当前模态视图(sheetfullScreenCover 等)。
  • 适用于 iOS 15+ ,在旧版本中需要使用 @Binding 控制关闭。

4. 旧版本(iOS 13-14)使用 @Binding 关闭

swift 复制代码
struct ContentView: View {
    @State private var isShowingSheet = false

    var body: some View {
        Button("Show Sheet") {
            isShowingSheet = true
        }
        .sheet(isPresented: $isShowingSheet) {
            SheetView(isPresented: $isShowingSheet)
        }
    }
}

struct SheetView: View {
    @Binding var isPresented: Bool

    var body: some View {
        Button("Close") {
            isPresented = false  // 手动关闭
        }
    }
}

适用场景:兼容 iOS 13-14 的代码。


.sheet vs .fullScreenCover

特性 .sheet .fullScreenCover
显示方式 从底部滑出(卡片式) 全屏覆盖
手势关闭 支持下滑关闭 默认不能手势关闭
适用场景 临时输入、简短信息 全屏内容(如登录页)

.fullScreenCover 示例

swift 复制代码
.fullScreenCover(isPresented: $isShowingFullScreen) {
    FullScreenView()
}

总结

  • .sheet 用于 模态显示一个非全屏视图(通常从底部滑出)。
  • 使用 @Environment(\.dismiss)(iOS 15+)或 @Binding(iOS 13-14)关闭。
  • 适用于 临时弹窗、表单输入、二级内容展示 等场景。

希望这个指南对你有帮助!🚀

相关推荐
静开4 分钟前
Skills和MCP 到底什么区别
前端·人工智能
伯远医学9 分钟前
RIP-seq 高分文献案例分享
java·前端·javascript·人工智能·算法·eclipse·html
hunterandroid10 分钟前
[鸿蒙从零到一] LazyForEach 复用陷阱与 KeyGenerator 设计实战
前端
Hilaku16 分钟前
Web Components 为什么火不起来?
前端·javascript·程序员
Liora_Yvonne21 分钟前
从数据库到 Vue 页面:用 LY Fullstack 完成第一个真实全栈业务模块
前端·后端·nestjs
hunterandroid26 分钟前
自定义 View 绘制与触摸冲突:从滑动卡顿到事件分发闭环
android·前端
vancece30 分钟前
JS实现堆 & 215.数组中的第K个最大元素
java·前端·javascript
lichenyang4531 小时前
NestJS + Socket.IO 鉴权、用户房间与幂等邀请
前端·后端
paopaokaka_luck1 小时前
基于springboot3+vue3+uniapp的剧本杀预约小程序(AI角色对话、协同过滤算法、地图Api、Echarts图形化分析)
java·前端·spring boot·学习·echarts
lichenyang4531 小时前
React 实时通知与异步竞态处理
前端·后端