在Swift / UIKit中,如果您不能在各种UIView类型中组合太多内容,那么如何将UIView的“基”类泛化到其他视图类型

kx1ctssn  于 2023-02-03  发布在  Swift
关注(0)|答案(2)|浏览(97)

说我有

class Plastic: UIView, SomeProto {
  override something {
    blah
  }
  override func layoutSubviews() {
    blah
  }
}

然后我有各种自定义视图GreenPlastic: PlasticYellowPlastic: Plastic等。
我想对堆栈视图做同样的事情。
目前我使用复制粘贴工程:

class PlasticForStackViews: UIStackView, SomeProto {
  //.. copy and paste in the identical code.
  //.. if I edit something in one, edit in both
}

注意,你不能在UIView类、layoutSubviews等中编写任何好的东西(除非我彻底误解了什么,如果我错了告诉我)。
(显然,如果当前的问题只是"添加角"之类的,通常可以使用扩展)。

  • (注意,这里假设"基类"中解决的各种问题适用于UIView和其他视图类型,例如堆栈视图。显然,您无法将特定于图像视图的内容泛化到其他视图类型的"类似基类"中。)*

这个问题有解决的办法吗?
手头的问题与协议解决方案完全不同,因为实际上,您无法在UIView类中组合(除非我彻底误解了什么,如果我错了请告诉我)任何好东西... layoutSubviews等。

nfs0ujit

nfs0ujit1#

你说
这和协议完全不同
但这是协议扩展的描述:
各种视图类的许多功能都是相同的,可以用相同的方法处理
如果你需要"覆盖"默认的实现,就把声明放在协议定义中,否则就不用麻烦了。

protocol PlasticProtocol: UIView {
  func something() -> String
}

// MARK: - internal
extension PlasticProtocol {
  func etc() {
    // …
  }

  func something() -> String {
    "default"
  }

  func variousBringupStuff() {
    // …
  }
}
// MARK: - PlasticProtocol
extension Plastic: PlasticProtocol {
  func something() -> String {
    "override"
  }
}
let plastic = Plastic()
plastic.something() // override
let plasticProtocol: some PlasticProtocol = plastic
plasticProtocol.something() // default

当你需要覆盖超类成员的时候,命名是很糟糕的,而且你仍然需要定义覆盖并调用super,但这比copypasta要好。
一个三个三个一个

qcbq4gxm

qcbq4gxm2#

class PlasticView: UIView, SomeProtocol {
    /// Apply all identical code here
}

class GreenPlasticView: PlasticView {
    /// Automatically inherits code from PlasticView
}

class YellowPlasticView: PlasticView {
    /// Automatically inherits code from PlasticView
}

相关问题