Skip to content

Instantly share code, notes, and snippets.

@Viranchee
Created May 4, 2020 23:24
Show Gist options
  • Save Viranchee/40f86e5afbd4e5e9ac22167537e20194 to your computer and use it in GitHub Desktop.
Save Viranchee/40f86e5afbd4e5e9ac22167537e20194 to your computer and use it in GitHub Desktop.
import UIKit
final class ViewController: UIViewController {
@IBOutlet var incrementButton: UIButton!
@IBOutlet var totalCount: UILabel!
var viewModel = ViewModel()
override func viewDidLoad() {
super.viewDidLoad()
// Here, I am explicitly putting `Self` in a Closure
// This is a Strong Reference
// You are free to make it into a weak reference, or either clear the ViewModel's properties to free it of holding reference to this ViewController
let incrementCountEffect: Effect<(count: Int, countLabel: String)> = { newCount in
self.totalCount.text = newCount.countLabel
}
viewModel.incrementCountEffect = incrementCountEffect
}
@IBAction func buttonTapped(_ sender: UIButton) {
viewModel.incrementCount()
}
}
typealias Effect<A> = ((A) -> ())
struct ViewModel {
private(set) var currentCount: Int = 0
var incrementCountEffect: Effect<(count: Int, countLabel: String)>? = nil
private let countLabelString: (Int) -> String = { value -> String in
return "Count is: \(value)"
}
mutating func incrementCount() {
currentCount += 1
let countLabel = countLabelString(currentCount)
incrementCountEffect?((count: currentCount, countLabel: countLabel))
}
// Call this method to dereference closures held by this object
mutating func dereference() {
incrementCountEffect = nil
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment