问题
I’m trying to come up with an protocol-oriented MVVM for my tableviewcells. I have lots of them.
my viewModel
protocol PlainTableViewCellModelType {
var backgroundColor : UIColor {get}
var textColor: UIColor {get}
var titleFont : UIFont {get }
var accessoryType : UITableViewCellAccessoryType {get}
var textLabelNumberOfLines: Int {get}
}
my view
protocol PlainTableViewCellType{
associatedtype viewModel : PlainTableViewCellModelType
func setupUI(forViewModel viewModel: viewModel)
}
my class
conformance
class PlainTableViewCell : CCTableViewCell, PlainTableViewCellType{
override init(style: UITableViewCellStyle, reuseIdentifier: String?) {
super.init(style: style, reuseIdentifier: reuseIdentifier)
}
required init?(coder aDecoder: NSCoder) {
fatalError()
}
func setupUI(forViewModel viewModel: PlainTableViewCellModelType){
contentView.backgroundColor = viewModel.backgroundColor
textLabel?.textColor = viewModel.textColor
textLabel?.font = viewModel.titleFont
accessoryType = viewModel.accessoryType
textLabel?.numberOfLines = viewModel.textLabelNumberOfLines
}
}
The current setups results in the following error:
Type 'PlainTableViewCell' does not conform to protocol 'PlainTableViewCellType'
I can get it to work if I do:
protocol PlainTableViewCellType{
func setupUI(forViewModel viewModel: PlainTableViewCellModelType)
}
But I want to have an associatedType
so I can enforce same model in all my PlainTableViewCellType
functions
EDIT: I'm happy to listen to alternatives, but first I want to know why this doesn't work.
回答1:
You must create PlainTableViewCellModelType
implementation and declare typealias
in cell implementation. Use it as type for parameter in setupUI(forViewModel:)
because compiler cant infer associated type.
protocol PlainTableViewCellModelType {
var backgroundColor : UIColor { get }
var textColor: UIColor { get }
var titleFont : UIFont { get }
var accessoryType : Int { get}
var textLabelNumberOfLines: Int { get }
}
protocol PlainTableViewCellType{
associatedtype viewModel : PlainTableViewCellModelType
func setupUI(forViewModel viewModel: viewModel)
}
struct PlainTableViewCellModel: PlainTableViewCellModelType {
var backgroundColor : UIColor
var textColor: UIColor
var titleFont : UIFont
var accessoryType : Int
var textLabelNumberOfLines: Int
}
class PlainTableViewCell : UITableViewCell, PlainTableViewCellType {
typealias viewModel = PlainTableViewCellModel
override init(style: UITableViewCell.CellStyle, reuseIdentifier: String?) {
super.init(style: style, reuseIdentifier: reuseIdentifier)
}
required init?(coder aDecoder: NSCoder) {
fatalError()
}
func setupUI(forViewModel viewModel: PlainTableViewCellModel) {
contentView.backgroundColor = viewModel.backgroundColor
textLabel?.textColor = viewModel.textColor
textLabel?.font = viewModel.titleFont
textLabel?.numberOfLines = viewModel.textLabelNumberOfLines
}
}
回答2:
In protocol you need remove PlainTableViewCellModelType:
protocol PlainTableViewCellType{
associatedtype viewModel
func setupUI(forViewModel viewModel: viewModel)
}
and in PlainTableViewCell you need add something like this:
typealias viewModel = PlainTableViewCellModelType
来源:https://stackoverflow.com/questions/52729852/how-can-i-correctly-use-associatedtype-in-my-protocol