-
Notifications
You must be signed in to change notification settings - Fork 1
About View Models
The role of a view model is to aggregate, transform or otherwise process model data to provide bound views with bindable data and on the other side to process user interface events and update model data or trigger other activities in response of such events.
Even though view models are responsible to support views and view bindings, they can and should be as independent from the concrete user interface as possible to enable reuse and provide flexibility.
In that sense, view models represent the state of an abstract user interaction that is implemented by some user interface.
For example, if the abstract user interaction is to edit a number value:
- The view model has a number property (f.e.
@property double value
), the state of the user interaction is the value of that property- The view model may also have a maximumValue property (f.e.
@property double maxValue
) that might depend on some system state and that determines the range of the number value
- The view model may also have a maximumValue property (f.e.
- The user interface can be a UIStepper, UISlider, a UITextField or some other control.
- User interface controls supporting a maximum value (f.e. UIStepper or UISlider) can make use of that property
The view model does not know anything about the user interface control that actually displays the data and thus can support all these rather different controls and changing the presentation does not require any code changes.
For the use case to display and edit a date value:
- The view model has a date property (NSDate), for example
@property NSDate* date
- If the rendering of the date depends on the state of the user interaction or some other system state, the view model can provide a formatter property that adapts to that state.
- The user interface could be a UILabel wrapped in a AKADatePickerKeyboardTriggerView (extension provided by beacon) or a UIDatePicker.
- The binding specifies a formatter
- The formatter can be specifically created an customized in the binding (see formatter bindings) if that presentation is unlikely to be reused in other places.
- The formatter can be provided by an application-wide enumeration of shared formatters and referenced from the binding, if the format is used in different places.
- The binding can reference a formatter provided by the view model, if the format depends on the abstract user interaction state.
Again, the view model does not (have to) know about the views presenting the date neither about formatting, unless the formatting is part of the abstract user interaction state.
As a consequence, the view model does not depend on visual aspects of the presentation, internationalization or localization (Storyboards support localization, so it makes sense that you define locale sensitive customizations there).
For simple use cases it is often convenient to let the view controller fulfill the role of a view model. This is a good choice if:
- The view controller is basically not doing anything else
- The view controller does not have presentation specific code (does not implement delegates, does not contain customization code that cannot be expressed in storyboards).
- It's unlikely that you want to reuse the view model in a different context.
The advantage is to save the extra class to define for the view model.
However, in non-trivial cases it is most often advisable to provide a separate view model for the obvious reasons (most importantly reuse and avoidance of spaghetti code clusters)