swift 分离UIViewController和UIView的

2020-06-17  本文已影响0人  wsj_2012

1、痛点

在常用的设计模式中,MVC在UI上的使用最为通用,但MVC最大的痛点就是Controller里面代码臃肿,代码结构性和可读性不强,这里提供一种解决此痛点的方案----UIViewController和UIView分离。

2、直接上解决方案实现

2.1、创建一个纯净的UIViewController的基类,通过泛型指定其内部要渲染的UIView。
class ViewController<Container: UIView>: UIViewController {

    var container: Container { view as! Container }
    
    override func loadView() {
        super.loadView()
        if view is Container {
            return
        }
        view = Container()
    }
}
2.2、所有的UIViewController继承自基类ViewController,并申明该控制器要渲染使用View类型
class HomeController: ViewController<HomeView> {

    override func viewDidLoad() {
        super.viewDidLoad()
        container.title =  ""
        container.image = UIImage(named: "")
    }
}
2.3、实现HomeView
class HomeView: UIView {
    private lazy var titleLabel = UILabel()
    private lazy var iconImageView = UIImageView()
  
    var title: string? {
        didSet {
            titleLabel.text = title
        }
    }

    var image: UIImage? {
        didSet {
                iconImageView.image = image
        }
    }
    
    override init(frame: CGRect) {
        super.init(frame: frame)
        
        titleLabel.textColor = .black
        titleLabel.font = .systemFont(ofSize: 13, weight: .semibold)
        
        iconImageView.contentMode = .scaleAspectFill
        
        addSubview(titleLabel)
        addSubview(iconImageView)
    }
    
    required init?(coder: NSCoder) {
        fatalError("init(coder:) has not been implemented")
    }
    
    override func layoutSubviews() {
        super.layoutSubviews()
        
        titleLabel.frame = .init(x: 100, y: 100, width: 100, height: 40)
        iconImageView.frame = .init(x: 100, y: 100, width: 100, height: 100)
    }
}
2.4、 使用
let homeCtl = HomeController()
present(controller: homeCtl, animated: true)

总结

使用简单,创建类就声明要渲染的View类型,可读性强。
Controller内代码纯净, Controller可更加专注与model和view的协调和调用,结构化清晰,职责更明确。

上一篇下一篇

猜你喜欢

热点阅读