gpt4 book ai didi

ios - 在 SwiftUI 中将模态表的大小从一半更改为完整动画

转载 作者:行者123 更新时间:2023-12-02 18:03:28 24 4
gpt4 key购买 nike

我希望某个 View 以半屏表格的形式开始,但是当它完成一些加载后,它应该转换为全屏表格。

所以在 UIKit 中我的解决方案是:

let vc = UIViewController()
vc.view.backgroundColor = .red
vc.sheetPresentationController?.detents = [.medium(), .large()]
self.present(vc, animated: true)

DispatchQueue.main.asyncAfter(deadline: .now() + .seconds(1)) {
vc.sheetPresentationController?.animateChanges {
vc.sheetPresentationController?.selectedDetentIdentifier = .large
}
}

这在 UIKit 中工作正常...但这在 SwiftUI 中也有可能吗?

SwiftUI 中的类似内容可能如下所示:

    struct ContentView: View {
@State var showSheet = false

var body: some View {
Button {
showSheet = true
} label: {
Text("Show-Sheet")
}
.sheet(isPresented: $showSheet, content: {
SheetView()
})
}
}

struct SheetView: View {
@State var showFullSheet = false

var body: some View {
Button {
withAnimation {
showFullSheet.toggle()
}
} label: {
Text("Toggle")
}
.presentationDetents(showFullSheet ? [.large] : [.medium, .large])
}
}

这基本上是可行的,但问题是一半和全部之间的过渡不是动画的。不过我需要动画。这在 SwiftUI 中是否可以以某种方式解决?因为我想将我呈现的 View 包装在一个 UIViewController 中,然后托管我现有的 SwiftUI View 将不是一个选项,因为呈现部分仍将由 swift-ui 完成,对吧?

最佳答案

首先使用presentationDetents(_:selection:)选择绑定(bind)跟踪您的 selectedDetent 状态。您遇到此动画问题的原因是,当您将 sheet 设置为 large 时,您设置的是 allow detents set only with [.large] 所以它是没有动画并直接跳到大。为了克服这个问题,我添加了 @State 属性以使用 presentationDetents 修饰符更新允许制动器。现在,如果您在更新 selectedDetent 状态后立即更新 detents set 那么它也不会显示动画,所以为了解决这个问题我添加了一秒钟的延迟来更新 detents,这将解决您的动画问题。

struct SheetView: View {
@State var selectedDetent: PresentationDetent = .medium

@State var detents: Set<PresentationDetent> = [.large, .medium]

var body: some View {
Button {
selectedDetent = selectedDetent == .large ? .medium : .large
} label: {
Text("Toggle")
}
.presentationDetents(detents, selection: $selectedDetent)
.onChange(of: selectedDetent) { newValue in
if newValue == .large {
updateDetentsWithDelay()
} else {
detents = [.large, .medium]
}
}
}

func updateDetentsWithDelay() {
Task {
//(1 second = 1_000_000_000 nanoseconds)
try? await Task.sleep(nanoseconds: 100_000_000)
guard selectedDetent == .large else { return }
detents = [.large]
}
}
}

关于ios - 在 SwiftUI 中将模态表的大小从一半更改为完整动画,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/73803597/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com