DEV Community

noah.k
noah.k

Posted on

Protocol Oriented Programming (POP) Brief Summary

Protocol Oriented Programming is a powerful approach when using Swift.

Imagine you want to add some functionality to some UIView.

  • Add a function of 360 degrees rotation with animation
  • Access borderColor property directly

How can you realize that?

1. Object Oriented Way

extension UIView {
    func rotate(duration: TimeInterval) {
        UIView.animate(withDuration: duration / 2, delay: 0.0, options: [.curveEaseIn], animations: {
            self.transform = self.transform.rotated(by: CGFloat.pi)
        }) { _ in
            UIView.animate(withDuration: duration / 2, delay: 0.0, options: [.curveEaseOut], animations: {
                self.transform = self.transform.rotated(by: CGFloat.pi)
            }, completion: nil)
        }
    }

    var borderColor: CGColor? {
        get {
            return layer.borderColor
        }
        set {
            layer.borderColor = newValue
        }
    }
}

var myView = UIView()
myView.rotate(duration: 1.0)
myView.borderColor = UIColor.green.cgColor
Enter fullscreen mode Exit fullscreen mode

Problem of Object Oriented Way

  • All UIView subclasses automatically inherit attributes and behaviors, even if you don't need them (code smells "Refused Bequest")
  • If you want to add more functionality and implement it to the extension, the extention keeps growing

2. Protocol Oriented Way

protocol Rotatable {
    func rotate(duration: TimeInterval)
}

extension Rotatable where Self: UIView {
    func rotate(duration: TimeInterval) {
        UIView.animate(withDuration: duration / 2, delay: 0.0, options: [.curveEaseIn], animations: {
            self.transform = self.transform.rotated(by: CGFloat.pi)
        }) { _ in
            UIView.animate(withDuration: duration / 2, delay: 0.0, options: [.curveEaseOut], animations: {
                self.transform = self.transform.rotated(by: CGFloat.pi)
            }, completion: nil)
        }
    }
}

protocol BorderColorable {
    var borderColor: CGColor? { get set }
}

extension BorderColorable where Self: UIView {
    var borderColor: CGColor? {
        get {
            return layer.borderColor
        }
        set {
            layer.borderColor = newValue
        }
    }
}

class MyView: UIView, Rotatable, BorderColorable {}

var myView = MyView()
myView.rotate(duration: 1.0)
myView.borderColor = UIColor.green.cgColor
Enter fullscreen mode Exit fullscreen mode

Points

Benefits of Protocol Oriented Way

  • Loose coupling : You can avoid inheriting unnecessary attributes or behaviors
  • Reusability : You can realize necessary and sufficient functionality, by separating protocols and implementing multiple protocols

Reference

LinkedIn Learning Swift 4: Protocol-Oriented Programming

Top comments (0)