【发布时间】:2021-09-06 00:28:41
【问题描述】:
我构建了一个自定义AsyncImage 视图,其中ImageLoader 类获取图像并在检索图像时更新视图。由于 @StateObject 仅在第一次构建视图时被初始化,如果从父级提供的 url 发生更改,我需要一种方法让 ImageLoader 获取新图像,我在底部使用 onChange(of: url)... 执行此操作。如果传递的父参数发生更改,是否可以这样做或者是否有更好的机制来更新 @StateObjects 参数?
struct URLImage: View, Equatable {
@StateObject private var loader = ImageLoader()
private var url: URL?
private var placeholder: UIImage?
init(url: URL?, placeholder: UIImage? = nil) {
self.url = url
self.placeholder = placeholder
}
var body: some View {
Image(uiImage: loader.image ?? UIImage())
.resizable()
.opacity(loader.isLoading ? 0 : 1)
.zIndex(5)
.overlay(
VStack {
if loader.isLoading {
ProgressView()
.progressViewStyle(CircularProgressViewStyle())
}
}
)
.background(
VStack {
if placeholder != nil && loader.isLoading == false && loader.image == nil {
GeometryReader { geo in
VStack(alignment: .center) {
Image(uiImage: placeholder!)
.resizable()
.aspectRatio(contentMode: .fit)
.frame(width: geo.size.width / 3)
.foregroundColor(Theme.Colors.primary400)
}
.frame(maxWidth: .infinity, maxHeight: .infinity, alignment: .center)
}
}
}
.frame(maxWidth: .infinity, maxHeight: .infinity)
.background(Theme.Colors.primary200)
)
.onAppear {
loader.url = url
}
.onChange(of: url) { newValue in
if loader.url != newValue {
loader.url = newValue
}
}
}
static func == (lhs: Self, rhs: Self) -> Bool {
lhs.url == rhs.url
}
}
【问题讨论】:
-
即使使用绑定,我也必须定义一个自定义
Binding,它有一个set,它会在更改时更新@StateObject。为什么这比我拥有它的方式有任何好处?