Controllers
The ability to define views and organize them is
important, but without the ability to do updates to the views
and respond to events from the views, the application is not as
dynamic as it could be. The controller is intended to respond to events from
the view and perform the necessary updates or queries to the model and return the results back to the view. In general, the controller has more information about the view.
A controller in
Dojo Toolkit can be a widget, like any other widgets in Dojo, and
can be instantiated programmatically or declaratively in HTML
markup. The main difference with a controller widget is that it
does not have any visible representation and does not display
anywhere in the view. Creating a basic controller widget is done
by extending the dijit._Widget
base widget subclass. That controller then inherits all the
widget life cycle capabilities of a Dojo widget as well as convenience
functions, such as widget connect() API that automatically handles
event cleanup on widget destruction. With
the parser and declaration system in Dojo 1.0 and higher,
controllers do not have to subclass dijit._Widget to get the markup
capability. Therefore if a particular controller does not need the widget life
cycle functions, then it does not need to extend dijit._Widget.
What a specific controller widget does is entirely
up to the developer; typically, however, it obtains references to widgets
contained within the view so that it can apply updates to the view as
data changes flow in through events. This widget can also
establish event
connections between widgets in the view so that when particular events
happen on the widget, other widgets are notified of that event. A common example of establishing these event connections would be in the case of a controller that binds to the onLoad event of a content pane it is monitoring. This action is usually done
because content pane containers might load data asynchronously, and the
controller cannot finish linking to all the widgets that are rendered in a ContentPane
container until the content pane container has finished loading and
initializing content. The controller also typically makes calls to
the data server service that provides access to the model and either retrieves
the data, or pushes changes to the data stored in that service.
Guidelines for controllers that are based on
the Dojo Toolkit
The Dojo Toolkit is flexible; therefore,
there are multiple techniques for implementing a controller pattern. The following
guidelines are provided for using Dojo Toolkit-based
applications.
- A controller manipulates a single
view and has general information only about that view and the widgets
contained in that view. Typically, a single view is represented
or contained by
the content pane widget, which contains a page of HTML that defines
the widgets that make up how that view represents data and
interacts with data.
- The controller only
responds to events from the view that it is manipulating and to special
case application-wide events that it explicitly registered to listen for, such as bringing a view into focus, refreshing all data displayed, and
so on. See the section on view-to-view communication
for more details. Graphically, these guidelines can be
represented by the following diagram:
- For views that are also containers
of other views, such as the tab container or accordion container
containers, each subview in the container has its own
controller.
The top-level controller connects and delegates actions
to the appropriate controller for the child views. The top-level
controller of a multiview container only knows about the
container view and how to manipulate it and how to communicate to the
child view
controllers. All contained view content manipulation is left to
the child-view controllers. Graphically, this guideline can
be represented by the following diagram:
The provided MVC example application
at the end of this topic applies the
guidelines noted previously. It makes use of the dojox.wire basic
controller code for declaratively defining actionable behaviors,
service invocations, and so on, for much of the controller logic,
including delegation to child controllers that is used in the example
application. The
example also
provides ways that a controller can bind to events on widgets
such
as a content pane widget, and use those events as part of its control of
the
view.