-
Notifications
You must be signed in to change notification settings - Fork 188
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
mvvm-delegates is not MVVM, actually that is MVP. #4
Comments
Those were the good arguments @marty-suzuki The point of ViewModel is to be reusable, which means it has no coupling to particular View components. On the other hand, Presenter is an entity that presents something and has some coupling to View. Basically Presenter is a decoupled logic from View layer into separate object. Whereas ViewModel is a “transformation” layer, that converts models to viewable format and the other way around. By no means these are the absolute rules, I wanted to share my thoughts related to this topic 😉 |
@marty-suzuki @jVirus amazing input, thanks for that! I totally agree with your explanation and I'll make a PR to fix it. You said:
Can you explain why delegation cannot be used as notification mechanism for MVVM? Lots of people were doing that in Obj-C times etc. Also, |
@tailec Notification mechanism for MVVM notifies without considering whatever objects receive notifications. On the other hand, notification mechanism with delegation pattern depends on anything object that outside of itself.
I think people used delegation pattern with MVC or MVP, not MVVM.
I'm sorry I didn't explain it enough 😅 By the way, what do you think differences between MVP and MVVM with delegation pattern? 👀 |
@marty-suzuki Replaced mvvm-delegates with mvp. |
Hello, the delegate does not need to know the specific implementation method. For ViewModel, I don't know what methods the view has. He just exposes some methods. What is the difference between a delegate and a closure? |
Hi, @VineFiner
Closures are one of Swift function that self-contained blocks of functionality. protocol SampleDelegate: AnyObject {
func sampleModel(_ sampleModel: SampleModel, didChange isEnabled: Bool)
}
class SampleModel {
private(set) var isEnabled: Bool = true
weak var delegate: SampleDelegate?
func toggle() {
isEnabled = !isEnabled
// Focus point①
// Calls a delegate method, therefore this model knows owner of delegate method
// even if a delegate object is abstracted.
delegate?.sampleModel(self, didChange: isEnabled)
}
}
class SampleViewController: UIViewController, SampleDelegate {
let button = UIButton()
let model = SampleModel()
func buttonHandler(_ button: UIButton) {
model.toggle()
}
func sampleModel(_ sampleModel: SampleModel, didChange isEnabled: Bool) {
button.isEnabled = isEnabled
}
} class SampleModel {
private(set) var isEnabled: Bool = true
var didChangeIsEnabled: ((Bool) -> Void)?
func toggle() {
isEnabled = !isEnabled
// Focus point②
// `didChangeIsEnabled` is owned by this model.
// Therefore, it only knows arguments and return values.
didChangeIsEnabled?(isEnabled)
}
}
class SampleViewController: UIViewController, SampleDelegate {
let button = UIButton()
let model = SampleModel()
func viewDidLoad() {
super.viewDidLoad()
// Focus point③
// Sets a closure with capturing self instance.
// But SampleModel don't know what instances captured (or not)
// when it calls.
model.didChangeIsEnabled = { [weak self] isEnabled in
self?.button.isEnabled = isEnabled
}
}
func buttonHandler(_ button: UIButton) {
model.toggle()
}
} |
"mvvm-delegates is not MVVM, actually that is MVP" - I think this explains the exact fundamental difference between MVP and MVVM. |
Hi, @tailec
ViewModel has a reference of abstracted ViewController as Delegate in mvvm-delegation.
It means that is not MVVM, actually that is MVP.
@amadeu01 mentioned in #2 (comment) , too.
I have a doubt about #2 (comment) .
I think differences between MVP and MVVM are those have references of View directly or not.
Presenter in MVP
Presenter has a reference of View (or ViewController) that is abstracted as protocol in almost cases.
To reflect state of Presenter, it calls method of abstructed View.
ViewModel in MVVM
ViewModel must not depend on View (or ViewController).
Even if View is abstracted as Protocol, ViewModel must not depend on them.
To reflect state of ViewModel, it notifies changes of state with closure (or RxSwift.Observable and so on).
Closure is implemented outside of ViewModel, therefore ViewModel does not depend on View directly.
The text was updated successfully, but these errors were encountered: