SwiftUI = ObservableObject 作为 Class 的选择

SwiftUI = ObservableObject as Choice of Class

使用 SwiftUI 我想按下一个按钮并让它切换用于过滤图像的 class。

在 SwiftUI 中,按钮将执行如下操作:

@ObservedObject var currentFilter = FilterChoice()
...
var body: some View {..
  Button(action:{
    print("clicked")
    var newFilter = Luminance()
    self.currentFilter = newFilter
  }) {
     Text("Switch to Luminance Filter")
  }
}

有一个 ObservableObject:

class FilterChoice: ObservableObject {  
    @Published var filter = Luminance()
}

它被 UIViewRepresentable 使用:

struct FilteredPhotoView: UIViewRepresentable {
  @ObservedObject var currentFilter = FilterChoice()

  func makeUIView(context: Context) -> UIView {
     ...
     // Code works and pulls correct filter but can not be changed
     let className = currentFilter.filter
     let filteredImage = testImage.filterWithOperation(className)
     ...   
  }...

目前,FilteredPhotoView 正在正确返回过滤后的图像。

但是如何使用 ObservedObject 来改变一个CLASS?

换句话说,ObservedObject 在这里正确设置了class:

class FilterChoice: ObservableObject {
   @Published var filter = Luminance()    
}

但是如何更改这个 ObservableObject 才能在 SwiftUI 中更改 class?例如,我想点击一个按钮,过滤器应该改为另一个class(例如:

new filter = ColorInversion()

我想我明白 ObservableObjects 是如何工作的,但我无法让它作为 class 的变化而不是像字符串值这样简单的东西来工作。

你真正需要的是一些泛型。

像这样声明一个协议:

protocol ImageFilter {

    func apply(to image: UIImage) // for example
}

在此处声明您的所有过滤器将共享且将由 FilterChoice 使用的任何方法或属性。 接下来声明您所有的过滤器都符合协议:

class Luminance: ImageFilter {
    // implement all the methods and properties declared in the protocol
    // for every filter
}

接下来声明您的 @Published 过滤器以符合该协议

class FilterChoice: ObservableObject {
    @Published var filter: ImageFilter

    public init(filter: ImageFilter) {
        self.filter = filter
    }

    // etc.
}

您将能够更改 @Published 使用的过滤器。