Monday, April 8, 2013

Base Mixin For Creating Widgets

The use of AMD became the standard way of writing custom widgets in v1.7 of the Dojo Toolkit. With the refactoring to AMD modules, a lot of utility functions that were located off of the root dojo module now need to be included in the require statement. As a result, I found myself writing the following code for each custom widgets I was creating:
define([
    "dojo/_base/config",
    "dojo/_base/declare",
    "dojo/_base/lang",
    "dojo/dom-attr",
    "dojo/dom-class",
    "dojo/dom-construct",
    "dojo/dom-style",
    "dojo/on",
    "dojo/Evented",
    "dijit/_Widget"
], function(config, declare, lang, domAttr, domClass, 
      domConstruct, domStyle, on, Evented, Widget){
    /* widget definition */
});
In an attempt to avoid always having to require these common modules, I have created a ComplexWidget mixin that will require these common modules and make them available as properties on the widget. This widget is released under the Apache License v2.0 and the latest code can be found here.
define([
 "dojo/_base/config",
 "dojo/_base/declare",
 "dojo/_base/kernel",
 "dojo/_base/lang",
 "dojo/dom-attr",
 "dojo/dom-class",
 "dojo/dom-construct",
 "dojo/dom-style",
 "dojo/on",
 "dojo/Evented",
 "dijit/_Widget"
], function(config, declare, kernel, lang, domAttr, domClass, 
      domConstruct, domStyle, on, Evented, Widget){
 
    return declare("evf/ComplexWidget", [Widget, Evented], {
  
        kernel: kernel,
  
        dojoConfig: config,
  
        lang: lang,
  
        domAttr: domAttr, 
  
        domClass: domClass, 
  
        domConstruct: domConstruct, 
  
        domStyle: domStyle,
  
        dojoOn: on,
  
        listen: function(target, type, listener, dontFix) {   
            var hndl = 
              on(target, type, this.hitch(listener), dontFix);
     
            this.own(hndl);
            return hndl;
        }, 
  
        hitch: function(fn) {
            return lang.hitch(this, fn);
        }
    });
});
Writing a custom widget looks like the following:
define([
    "dojo/_base/declare",
    "evf/CustomWidget"
], function(declare, ComplexWidget){

    return declare("myApp/MyWidget", [ComplexWidget], {        

        postCreate: function(){
            this.inherited(arguments);
            this.domClass.add(this.domNode, 'MyWidgetCssClass');
        }
    });
});

The result is easy access to commonly used modules without having to write a lot of boilerplate code.

No comments:

Post a Comment