Skip to content

Latest commit

 

History

History
executable file
·
1276 lines (854 loc) · 47.3 KB

1.8.rst

File metadata and controls

executable file
·
1276 lines (854 loc) · 47.3 KB

Dojo 1.8 Release Notes

The following browsers have been tested and are supported in this release. If a browser version is not listed as supported, it still may work, especially on browsers with rapid release cycles (Chrome, Firefox). Future minor releases of Dojo might include fixes to support future releases of these browsers, but we cannot guarantee it.

Desktop

  • Firefox 3.6-12 (Dojo 1.8.2+ also support Firefox 13-17)
  • Safari 5-6
  • Chrome 13-21
  • IE 6-9 (Dojo 1.8.4+ also support IE10, 1.8.6+ also support IE11)
  • Opera 10.50-12 (Dojo core only)

Mobile (dojox/mobile)

  • iOS 4.x, 5.x (Mobile Safari) (including all Dijit widgets except Editor) (Dojo 1.8.2+ also supports iOS 6.x)
  • Android 2.2-2.3, 3.1-3.2, 4.0-4.1 (Platform browser)
  • BlackBerry 6-7 (Platform browser)
  • Mobile compatibility on desktop browsers: IE 8-9, Firefox 4-12, Safari 5-6, Chrome 13-19

TODO: Link to page with specific vendor device models tested on

Server-Side Platforms

  • While not a browser, Dojo 1.8 also works inside Node 0.6.x and 0.8.x.
  • packageMap was deprecated in lieu of the proposed AMD standard map configuration; see AMD map
  • module-level configuration as per the proposed AMD standard
  • legacy asynchronous performance has been improved.
  • dojo/_base/Deferred was deprecated in lieu of dojo/Deferred. It was updated to utilize the new promise architecture and maintains its legacy API, but developers should transition to dojo/Deferred. Also, dojo/_base/Deferred::when() has been deprecated in lieu of dojo/when.
  • dojo/_base/xhr was deprecated in lieu of dojo/request/xhr. It was updated to utilize the new request architecture, but developers should transition to dojo/request/xhr.
  • dojo/_base/sniff was deprecated in lieu of dojo/sniff. It was updated to utilize the new sniff module, but developers should transition to dojo/sniff.
  • dojo/dnd was enhanced to work on touch devices.
  • A new implementation of dojo/Deferred based on dojo/promise. It only supports the "modern" promise syntax (e.g. .then() instead of .addCallback() and .addErrback()). It is strongly recommended that you migrate from dojo/_base/Deferred and adopt the new API. See :ref:`dojo/Deferred <dojo/Deferred>`.
  • While dojo/DeferredList is not changed, it is deprecated in lieu of dojo/promise/all and dojo/promise/first.
  • The dijit/hccss module has moved to dojo core, with a stub left in dijit for backwards compatibility.
  • dojo/html::_ContentSetter is now async aware when it comes to parsing content being set. The promise returned from dojo/parser::parse() will be stored in parseDeferred. If using _ContentSetter directly, ensure that you use the parserDeferred to detect when the parsing is actually complete. For example:
.. js ::

  require(["dojo/html", "dojo/when"], function(html, when){
    var setter = new html._ContentSetter({
      node: someNode,
      parseContent: true
    });
    setter.set(someContent);
    when(setter.parseDeferred, function(){
      // Do something
    });
  });
  • dojo/io/iframe has was deprecated in lieu of dojo/request/iframe. It was updated to utilise the new request architecture, but developers should transition to dojo/request/iframe.
  • dojo/io/script has was deprecated in lieu of dojo/request/script. It was updated to utilise the new request architecture, but developers should transition to dojo/request/script.
  • dojo/node is an AMD plugin that allows easier loading of Node.js modules when running Dojo in Node.js. See :ref:`dojo/node <dojo/node>` for more information.

There are several enhancements to dojo/parser:

  • The Parser now supports the use of Module IDs (MID) when specifying the data-dojo-type in declarative markup (#13778). Developers should use the MID in their code to ensure future compatibility with baseless modules. See below for information on Auto Require which compliments this feature.

An example:

.. js ::

  require(["dojo/parser", "dojo/ready", "dijit/form/Button", "dijit/layout/ContentPane"],
    function(parser, ready){
      ready(function(){
        parser.parse();
      });
    }
  );
.. html ::

  <div data-dojo-type="dijit/layout/ContentPane">
    <button data-dojo-type="dijit/form/Button">Click Me!</button>
  </div>
  • The parser now also supports a new data-dojo-mixins attribute that allows to dynamically mixin one or several classes into the main data-dojo-type class as follows:
.. js ::

  require(["dojo/parser", "dojox/treemap/TreeMap", "dojox/treemap/Keyboard", "dojox/treemap/DrillDownUp"],
    function(parser) {
      parser.parse();
    }
  );
.. html ::

  <div data-dojo-type="dojox/treemap/TreeMap"
    data-dojo-mixins="dojox/treemap/Keyboard, dojox/treemap/DrillDownUp"></div>
  • There is also a new method construct() that is useful for when you have a widget constructor and want to apply it to a node that may or may not have data-dojo-type specified:
.. js ::

  require(["dojo/parser", "dojo/query", "dijit/form/Slider"],
  function(parser, query, Slider){
    query("input[type=slider]").forEach(function(node){
      parser.construct(Slider, node);
    }
  }
  • The parser now fully supports the declarative script tags with a type="dojo/aspect" (#15117). This allows you to define scripts that run in line with the aspect concepts behind aspect programming used in the :ref:`dojo/aspect <dojo/aspect>` module.

Each of the following is possible:

.. html ::

  <div data-dojo-type="package/module" data-dojo-props="foo:'bar'">

    <!-- A script with "before" advice -->
    <script type="dojo/aspect" data-dojo-advice="before" data-dojo-method="method1" data-dojo-args="i">
      console.log("I ran before!");
      i++; // Modify an argument
      return [i]; // Return the modified argument to be used by the original method
    </script>

    <!-- A script with "around" advice -->
    <script type="dojo/aspect" data-dojo-advice="around" data-dojo-method="method2" data-dojo-args="origFn">
      return function(){ // you have to be a factory and return a function
        console.log("I ran before!");
        origFn.call(this); // With around advice, you have to call the original method
        console.log("I ran after!");
      });
    </script>

    <!-- A script with "after" advice -->
    <script type="dojo/aspect" data-dojo-advice="after" data-dojo-method="method3">
      console.log("I ran after!");
    </script>

  </div>

Note with the addition of this coupled with the support of script tags of type="dojo/on", it does mean that script tags of type="dojo/connect" are fully deprecated and will likely be dropped in 2.0. In fact, internally the parser uses dojo/aspect to accomplish a connect.

  • The parser now supports the ability to require modules declaratively (#15118). This is accomplished using the <script type="dojo/require"> tag. Before the document is scanned and parsed, the parser will look for any <script> tags of type dojo/require and the parser will attempt to load any modules identified in the hash that is contained within the text of the tag and put it in the global scope. For example:
.. html ::

  <script type="dojo/require">
    on: "dojo/on",
    "app.registry": "dijit/registry",
    Button: "dijit/layout/button"
  </script>

See :ref:`Parser Declarative Require <dojo/parser#declarative-require>` for more information.

  • The parser now supports the ability to automatically require in modules when encountered declaratively (#14591). As the document is being scanned and parsed, but before the widgets are instantiated, the parser will automatically attempt to require in modules that it hasn't been able to resolve a constructor for and the data-dojo-type looks like a MID (e.g. package/module).

Note Developers should really be cautious when using this feature, because you are not making your dependencies clear, you may have a harder time isolating where your issue is, because the parser is automatically loading modules that you may not be consciously aware of.

By setting isDebug to true in your dojoConfig, the dojo/parser will log to the console warnings whenever it attempts to auto-load modules, so this feature is not used unintentionally.

.. code-example ::

  Here is an example of the feature in action.  Notice how no modules are required.

  .. html ::

    <input type="text" name="field1" data-dojo-type="dijit/form/TextBox" value="Hello World" />
    <button type="button" data-dojo-type="dijit/form/Button">Button</button>

See :ref:`Parser Auto Require <dojo/parser#auto-require>` for more information.

  • Because of the nature of AMD and require(), when you use either the declarative require feature or the auto require feature, .parse() will operate in an asynchronous mode. In order to maintain backwards compatibility though, the results of .parser() continue to be an Array, but will also have a promise mixed in which is fulfilled with the results of the .parse(). For new development, the safest way to interact with .parse() is to treat the return as a promise. For example:
.. js ::

  require(["dojo/parser"], function(parser){
    parser.parse().then(function(instances){
      // instances contains the instantiated objects
    });
  });
  • The dojo/_base/sniff module was superseded by dojo/sniff. dojo/sniff functions the same way as the old module, except doesn't set globals like dojo.isIE. Instead, use has("ie") etc.
  • The class now supports custom accessors for Object properties (#15187). This is similar to the functionality in dijit/_WidgetBase. Setting a custom accessor in the format of _xxxSetter or _xxxGetter will automagically be called when set() or get() or invoked. For example:
.. js ::

  require(["dojo/Stateful", "dojo/_base/declare"], function(Stateful, declare){
    var aClass = declare(null, {
      foo: null,
      _fooGetter: function(){
        return this.foo;
      },
      _fooSetter: function(value){
        this.foo = value;
      }
    });

    var aInstance = new aClass();

    aInstance.set("foo", "bar");
    aInstance.get("foo");
  });
  • In addition, custom setters that will not be setting an attribute immediately (for example doing an XHR request to transform a value) can return a promise and the attribute watches, if any, will not be called until the promise is fulfilled.
  • There is a helper function directly setting the value of an attribute/property named _changeAttrValue that is intended for use when you have co-dependent values where calling set() is not appropriate, like when a value is set on a widget the checked state needs to change as well.

See :ref:`dojo/Stateful <dojo/Stateful>` for further information.

  • The module was enhanced to support touch.over, touch.out, touch.enter and touch.leave synthetic events similar to mouseover, mouseout, mouseenter, and mouseleave.
  • In addition, touch.move on mobile was changed to work like mousemove on desktop, so that when connecting to a DOMNode:
.. js ::

  require(["dojo/on", "dojo/touch"], function(on, touch){
    on(node, touch.move, function(e){
      // handle event here
    });
  });

Note It fires whenever and only when the finger is dragged over the specified node, regardless of where the drag started. Behavior when connecting to a document is unchanged.

  • Widget events, including attribute changes, are emitted as events on the DOM tree
.. js ::

  on(dom.byId("buttonContainer"), "click", function(evt){
    var widget = registry.getEnclosingWidget(evt.target);
    if(widget){
      console.log("click on widget " + widget.id);
    }
  });

See :ref:`Widget events published to the DOM <quickstart/events#widget-events-published-to-the-dom>` for details.

  • Attribute setters specified with string values can now point to sub-widgets as well as DOMNodes, for example:
.. js ::

  dojo.declare("MyWidget",
    [dijit._WidgetBase, dijit._TemplatedMixin, dijit._WidgetsInTemplateMixin], {

    templateString:
      "<div>" +
        "<button data-dojo-type='dijit/form/Button'
          data-dojo-attach-point='buttonWidget'>hi</button>" +
        "<input data-dojo-attach-point='focusNode'>" +
      "</div>"

    // Mapping this.label to this.buttonWidget.label
    label: "",
    _setLabelAttr: "buttonWidget",

    // Mapping this.value to this.focusNode DOMNode
    value: "",
    _setValueAttr: "focusNode",
  });
  • childWidget.placeAt(parentWidgetId) now works correctly, even when the parent is a container widget. I.e. placeAt() calls parentWidget.addChild(). Note that you will have problems if there is a DOMNode outside of the parent widget with the same ID as the parent widget. In that case, the id argument becomes ambiguous.
  • Can now accept a String for the value parameter (either as an argument to the constructor, or to set("value", ...).
.. js ::

  require(["dijit/Calendar"], {
    var calendar = new Calendar({value: "2011-12-25"});
  });
  • ContentPane now supports addChild() and removeChild(). However, the behavior of addChild(widget, index) is undefined if the ContentPane already contains random HTML. It's intended to be used when the pane contains just a list of widgets, like Toolbar or BorderContainer.
  • dijit/layout/ContentPane::addChild(child) will not call resize() on the new child widgets, so it should be used carefully on ContentPanes inside of a layout widget hierarchy. Note that resize() only works on visible widgets, not hidden widgets such as unselected tabs of a TabContainer.
  • ContentPane is now async aware when setting its content via the ContentSetter.
  • DateTextBox's drop down Calendar no longer automatically opens upon clicking the input area, unless the hasDownArrow=false option is set (in which case that's the only way to open the drop down Calendar). (#14142)
  • dijit/Destroyable is new utility mixin to track handles of an instance, and then destroy them when the instance is destroyed. The application must call destroy() on the instance in order to release the handles.

    This functionality was extracted from dijit/_WigetBase and most users will access it through dijit/_WidgetBase (or a subclass).

Example usage:

.. js ::

  var DestroyableSubClass = declare(Destroyable, {
    constructor: function(aStatefulObject){
      var self = this;
      this.domNode = domConstruct.create("button");
      this.own(
        // setup an event handler (automatically remove() when I'm destroyed)
        on(this.domNode, "click", function(){ ... }),

        // watch external object (automatically unwatch() when I'm destroyed)
        aStatefulObject.watch("x", function(name, oVal, nVal){ ... }),

        // create a supporting (internal) widget, to be destroyed when I'm destroyed
        new MySupportingWidget(...)
      );
    }
  });
  • Sizing improved for when Dialog is too big to fit in viewport. Also, sizing automatically adjusts if users resizes the browser window. (#14147)
  • Performance fixes for editors with lots of text (#14231)

The Menu widget has two new (optional) attributes:

  • selector:

    CSS selector that specifies that the Menu should be attached, via event delegation, to matching subnodes of targetNodeIds, rather than the targetNodeIds nodes themselves.

  • currentTarget:

    (readonly) which node the menu is being displayed for

Together, they allow a single Menu to attach to multiple nodes through delegation, and for the Menu's action to be adjusted depending on the node. For example:

.. js ::

  require(["dijit/registry", "dijit/Menu", "dijit/MenuItem", "dojo/query!css2"], function(registry, Menu, MenuItem){
    var menu = new Menu({
      targetNodeIds: ["myTable"],
      selector: "td.foo"
    });
    menu.addChild(new MenuItem({
      label: "click me"
      onClick: function(evt){
        var node = this.getParent().currentTarget;
        console.log("menu clicked for node ", node);
      }
    }));
  });

This will track right-click events on each cell of a table with class="foo".

Further, the targetNode's contents can be changed freely after the Menu is created. Nodes matching the selector can be created or removed, and no calls to bindDomNode() or unBindDomNode() are necessary.

Note that, like :ref:`dojo/on::selector() <dojo/on#selector-function>`, you need to require() an appropriate level of dojo/query to handle your selector.

  • You can now disable tabs by setting the disabled property of the pane:
.. js ::

    pane.set("disabled", true);

The Tooltip widget has two new (optional) parameters:

  • selector:

    CSS selector that specifies that the Tooltip should be attached, via event delegation, to matching subnodes of the connectId node, rather than the connectId itself.

  • getContent():

    lets the app customize the tooltip text that's displayed based on the node that triggered the tooltip.

These parameters allow a single Tooltip widget to display unique tooltips for (for example) each row in a table:

.. js ::

  require(["dijit/Tooltip"], function(Tooltip){
    var tooltip = new Tooltip({
      connectId: myTable,
      selector: "tr",
      getContent: function(matchedNode){ return ...; /* String */ }
    });
  });

Further, the table contents can be changed freely after the Tooltip is created. Rows can be created, removed, or modified, and no calls to the Tooltip widget are necessary.

Another example: specifying selector=".dijitTreeRow" will track mouseenter and mouseleave events on each row of a Tree, rather than merely monitoring mouseenter/mouseleave on the Tree itself.

Note that, like :ref:`dojo/on::selector() <dojo/on#selector-function>`, you need to require() an appropriate level of dojo/query to handle your selector.

All browsers except IE now implement shading in the claro theme via CSS gradients, rather than by using images. This reduces the number of files downloaded, speeding up page load.

Also, the remaining gradient images files (for IE) no longer contain any blue. Thus, customizing claro to a different color does not require modifying those files. You are still required however to update icon files that contain the theme's primary color, such as:

  • Checkboxes and radio buttons
  • The slider handles
  • Calendar arrows
  • Dialog and TabContainer close icons
  • etc.

There have been many performance improvements to dijit:

  • CSS gradients used in claro (see above)
  • dijit/_CssStateMixin now creates listeners at the document level, rather than separate listeners for each widget. This speeds up page instantiation time, especially on a page with many small widgets like TextBoxes, Buttons, Trees (because of the many rows of the Tree), and Menus.
  • Similar event delegation changes were made for Menu and Tree, putting the listeners on the Menu or Tree rather than each individual MenuItem/TreeNode.
  • Performance improvement for TabContainers with closable tabs, because only one close Menu is created per TabContainer, rather than one Menu per tab. Event handling was also moved to TabContainer level rather than at each individual tab.
  • A new dropLabels mode was introduced on axis. It is true by default and allows to drop superfluous labels on the axis. Note that in some cases this might slow down a bit the initial computation of the chart. You can avoid that or come back to the previous behavior by:

    • setting dropLabels to false (but then you don't get the automatic drop labels)
    • setting minorLabels to false if you know minorLabels won't show up anyway
  • Bars, Columns and their stacked versions as well as Pie plots now support drop shadow property.

  • dojox/charting/widget classes now inherits from dijit/_WidgetBase instead of dijit/_Widget.

  • Base class for themes is now SimpleTheme instead of Theme. Themes that require gradients still need to use Theme which now inherits from SimpleTheme.

  • Provide a styleFunc on the various plots to allow to dynamically style the plot items.

  • Improve the management of missing data point in line-based plot by providing a interpolate option.

  • A new Calendar component is introduced in dojox/calendar package. It displays events from a data store over a time duration and allows the interactive editing of the position in time and duration of these events. See :ref:`dojox/calendar <dojox/calendar>`.
  • The CometD library has been removed from DojoX. The CometD project now maintains its own Dojo library in AMD format as part of their project. This will be available via cpm, or may be downloaded from GitHub. See: CometD Project.
  • A new gauges package is introduced in dojox/dgauges package. It provides a fully extensible gauges framework allowing you to create your own gauges as well as predefined, ready to use gauge widgets. Both circular and rectangular gauges (horizontal and vertical) are supported. See :ref:`dojox/dgauges <dojox/dgauges>`.
  • Updated source code to AMD, and refactored to use recent advances to the Dojo APIs.
  • Updated source code to AMD, and refactored to use recent advances to the Dojo APIs, for dojox/widget/Calendar and associated widgets.
  • The dojox/data/LightstreamerStore has been removed from DojoX. The Lightstreamer project now maintains its own Dojo library in AMD format as part of their project. This will be available via cpm, or may be downloaded from GitHub. See: Lightstreamer.
  • A new Treemap component is introduced in the dojox/treemap package. It displays data as a set of colored, potentially nested, rectangular cells. Treemaps can be used to explore large data sets by using convenient drill-down capabilities. They reveal data patterns and trends easily. See :ref:`dojox/treemap <dojox/treemap>`.

The following Dojo Mobile widgets are new in Dojo 1.8. Click each widget name for details:

  • stopParser

    To support dojox/mvc, the stopParser feature was added to dojox/mobile/parser. If a widget has the stopParser flag, the parser stops parsing its child widgets. dojo/parser has this capability, but dojox/mobile/parser didn't until 1.8 to keep the code size small.

  • New data-dojo-type syntax

    dojox/mobile/parser accepts the new data-dojo-type syntax using the MID (e.g. data-dojo-type="dijit/form/Button").

  • Function type property

    dojox.mobile.parser handles function-type properties correctly. In the following example, the onClick() method of the ListItem widget is overridden by the myClick function.

.. html ::

  <li data-dojo-type="dojox.mobile.ListItem"
      data-dojo-props='moveTo:"bar", onClick:myClick'>
      Slide
  </li>
  • A webkit-mobile build profile was added to eliminate IE etc. code paths from a build intended only to run on webkit-mobile devices.

To create this special build:

$ cd util/buildscripts/
$ ./build.sh releaseDir=... action=release optimize=closure profile=webkitMobile
  • The GFX API now supports clipping at shape level via the new Shape.setClip(clipGeometry) method. The possible clipping geometry types are rectangle, ellipse, polyline and path (vml only supports rectangle clipping, while the GFX silverlight renderer does not support path clipping.
  • A new Shape.destroy() method has been added to properly dispose a shape when it is not used anymore. The Group.clear() method has been updated to take an optional boolean parameter that indicates whether the group children should be disposed while clearing the group.
  • The Group.getBoundingBox() method now returns the children bounding rectangle.
  • New modules specific to the SVG and canvas renderers have been added, respectively dojox/gfx/svgext and dojox/gfx/canvasext. The purpose of these modules is to give the user access to the specific capabilities of the renderer:
    • canvasext defines new methods enabling access to the Canvas pixel manipulation API, via the new Surface.getContext(), Surface.getImageData() and the Surface.render() public method.
    • svgext defines a new Shape.addRenderingOption(option, value) that adds the specified SVG rendering option on this shape, as specified by the SVG specification.
  • The MVC API now supports binding to attributes in addition to value, along with support to transform data and support one way binding to or from a model in addition to the support for two way binding.
  • :ref:`dojox/mvc/StatefulModel <dojox/mvc/StatefulModel>` has been deprecated in favor of different controller options which give the developer more flexibility.

See :ref:`dojox/mvc <dojox/mvc>` for more information.

  • dojox/app framework now gives a clearer MVC structure by providing application controllers (dojox/app/Controller), view objects (dojox/app/View) and integration with data model/binding (dojox/mvc):
    • dojox/app/view has been removed, use dojox/app/View to create the view instance and render view widget.
    • dojox/app/scene has been removed, dojox/app/View can have parent view and children views removing the need for a specific object.
    • dojox/app/bind has been removed, use dojox/mvc controllers which give the developer more flexibility.
    • dojox/app/Controller has been added to add more flexibility in controlling the application, several controllers are provided in dojox/app/controllers package: Load controller, Transition controller, Layout controller and History controller
    • dojox/app/widgets/Container has been added as a scrollable and layout widget.

See :ref:`dojox/app <dojox/app>` for more information.

  • The documentation scripts at docscripts have been deprecated and replaced with a new documentation parser that works properly with AMD modules.

The builder supports the ability to detect declarative dependencies (both auto-requirement and declarative require modules) in static files and allow the building of them into a layer (#15367). To have resources scanned for dependencies, add them to the include array of a layer and tag them as declarative:

.. js ::

  var profile = {
    action: "release",

    packages:[{
      name: "dojo",
      location: "./dojo"
    },{
      name: "app",
      location: "./app"
    }],

    layers: {
      "app/main": {
        include: ["app/index.html"]
      }
    },

    resourceTags: {
      declarative: function(filename){
        return /\.htm(l)?$/.test(filename);
      }
    }
  };

See :ref:`depsDeclarative <build/transforms/depsDeclarative>` for more information.

While docscripts is still included in our releases, it's deprecated, and no longer used to generate dojo's own documentation. Nor is it expected to work well with AMD modules.

The documentation is now generated using https://github.com/wkeese/js-doc-parse.git. See https://github.com/wkeese/api-viewer/blob/master/README.rst for detailed instructions.

  • tracTreemap: a Treemap demo visualizing Trac ticket status
  • calendar: a Calendar component demo
  • todoApp: a "ToDo" application leveraging dojox/mobile, dojox/app & dojox/mvc packages
  • parserAutoRequire: a demonstration application for the auto-requirement and declarative requirement features of dojo/parser
  • The dojo/parser can operate in an async fashion when running under async: true configuration and using auto-require or declarative require features. If the results of parse() are needed, utilise the returned promise. Also any errors encountered during the parse will be raised as a promise errback.
  • Constructor Parameters: Execution of custom setters during widget construction has slightly changed. This may affect custom widgets that adjust widget parameters in postMixInProperties().

    As before, during initialization, _setXyzAttr(val) is called for each attribute xyz is passed to the constructor where the attribute has a corresponding _setXyzAttr() function or string. The change is that the value passed is the value specified to the constructor, rather than this.xyz. In other words, given a widget like:

    .. js ::
    
      declare("MyWidget", {
        this.xyz: "",
        postMixInProperties: function(){
          this.xyz = "dog";
        },
        _setXyzAttr(val){
          // ...
        }
      };
    

    and then calling the constructor with a custom value:

    .. js ::
    
      new MyWidget({ xyz: "cat" });
    

    _setXyzAttr("cat") would be called, rather than _setXyzAttr("dog") as before.

  • Connecting to dijit/Menu::_openMyself(): If you have menus on Trees etc. where you have connected to the private method dojo/Menu::_openMyself(), you should switch to the pattern shown above in the Menu section.
  • In the event passed to dijit/MenuItem::onClick(evt), evt.currentTarget now refers to the Menu.domNode, rather than the MenuItem.domNode. You can access the MenuItem via this, assuming that you haven't overridden the value of this, or alternately registry.getEnclosingWidget(evt.target).
  • Due to the event delegation performance improvements, if you have a custom template for MenuItem, remove the data-dojo-attach-event="..." attribute.
  • If you have a custom popup widget with a handleKey() method, and it is accessing evt.charOrCode or evt.charCode, you should change it to access evt.keyCode instead. Change evt.charOrCode == " " to evt.keyCode == keys.SPACE.

    Details: Some widgets used as dropdowns have a handleKey() method; handleKey() is called from _HasDropDown when the focus is on the _HasDropDown widget but the dropdown is open, and the user types a key. This delegates the keystroke to be processed by the dropdown widget. An example is ComboBox, where focus stays in the INPUT, but the up/down arrow keys affect which choice is shown in the drop down menu.

    The event passed to handleKey() is now a keydown event, rather than a synthetic keypress event generated from dojo.connect().

  • If you have a custom StackController or TabController subclass where the buttons for each pane have nested close buttons (like TabContainer itself, with the [x] on the right of each tab), you need to either:

    1. In your subclass's definition, set buttonWidgetCloseClass to the CSS class set on your close button.
    2. If your subclass extends TabController, set the dijitTabCloseButton CSS class on your close button, otherwise set dijitStackCloseButton.
  • Due to the event delegation performance improvements, if you have a custom template for TabButton, remove the data-dojo-attach-event="..." attribute.

  • Like with Menu, in the event passed to dijit/Tree::onClick(item, node, evt), and dijit/Tree::onDblClick(item, node, evt), evt.currentTarget now refers to the Tree.domNode, rather than the TreeNode.domNode. You can access the TreeNode via the node parameter.
  • If selected TreeNodes are highlighted strangely, you've probably created the Tree programatically without calling startup(). You need to call startup() on it after it's been attached to the DOM.
  • Due to the event delegation performance improvements, if you have a custom template for TreeNode, remove the data-dojo-attach-event="..." attribute.
  • Because of the asynchronous nature of the dojo/parser, when setting content (.set("content", content)) and that content is required to be parsed, the function can behave in an asynchronous way. Utilise the returned promise from the function to detect when the content is fully set. This function already returned a Deferred promise, because of the asynchronous nature XHR requests, but could still behave synchronously when not setting a URL.
  • dojox/charting/Theme used to be automatically required by dojox/charting/Chart. This is not the case anymore, if you use it, you need to explicitly require it in your application.

  • The new dropLabels mode of the axis is set to true by default if you experience missing labels and want to get back to previous behavior you might try to:

    • set dropLabels to false
    • set minorLabels to false if there are minorLabels that appear and were not previously
  • dojox/charting/plot2d/Pie now by default display 0 sized slices labels. You can set omitLabels to true to avoid that.

  • The dojox/mobile/migrationAssist module helps you migrate your dojox/mobile applications from 1.6/1.7 to 1.8. To enable migrationAssist, all you need to do is require this module as shown in the examples below.

    Legacy mode example:

    .. js ::
    
      dojo.require("dojox.mobile.migrationAssist");
      dojo.require("dojox.mobile"); // This is a mobile app.
      // ...
    

    AMD Style example:

    .. js ::
    
      require([
        "dojox/mobile/migrationAssist",
        "dojox/mobile", // This is a mobile app.
        // ....
      ]);
    

    If your application uses deprecated or no longer available functions, this module detects them and displays messages in the browser console.

    Also, it tries to dynamically fix them as much as possible so that the target application can work somehow. For example, dojox/mobile/View is no longer a container-type widget, and thus you cannot use addChild to add a child widget to View. This module dynamically inserts the addChild method into View in case the application is using it.

    Note, however, that the purpose of migrationAssist is not to run the older applications as they are, but to assist migration.

The remainder of this section gives a complete list of changes in dojox/mobile that may require a modification to your application, so you can also migrate your application without using the migrationAssist module.

  • FixedSplitter.css is no longer in the themes/common folder. It is in the device themes folders. (e.g. themes/iphone/FixedSplitter.css)
  • FlippableView was deprecated in 1.7, and removed in 1.8. Use SwapView instead.
  • The sync property is no longer supported. It always behaves asynchronously.
  • The btnClass property is no longer supported. Use rightIcon instead.
  • The btnClass2 property is no longer supported. Use rightIcon2 instead.
  • SpinWheel.css is no longer in the themes/common folder. It is in the devices themes folder. (e.g. themes/iphone/SpinWheel.css)
  • getValue() is no longer supported. Use get("values") instead.
  • setValue() is no longer supported. Use set("values", newValue) instead.
  • getValue() is no longer supported. Use get("value") instead.
  • getKey() is no longer supported. Use get("key") instead.
  • setValue() is no longer supported. Use set("value", newValue) instead.
  • When you place it in a ListItem, class="mblItemSwitch" is no longer necessary.
  • In 1.7 and prior, barType="segmentedControl" produced different UIs according to the current theme. In the iphone theme, it was a segmented control, but in other themes, it was tabs with or without icons. In 1.8, however, barType="segmentedControl" always produces a segmented control UI regardless of the current theme.

    If you still need the old behavior the following:

    .. js ::
    
      barType:{ "iphone_theme": "segmentedControl", "*": "tallTab" }
    

    Should produce a segmented control for the iphone theme, and a tall tab bar for the other themes. You need to use deviceTheme.js to specify barType that way.

  • Also, if you want to hide the tab icons of the segmented control in the iphone theme, you could apply the CSS like this:

    .. css ::
    
      .iphone_theme .mblTabBarSegmentedControl .mblTabBarButtonIconArea {
        display: none;
      }
    

    See test_ScrollableView-demo.html for an example usage.

  • Specifying a DOM Button with the class attribute like class="mblDomButtonWhitePlus" is no longer supported. Use icon="mblDomButtonWhitePlus" instead.
  • select() and deselect() are no longer supported. Use set("selected", boolean) instead.
  • Specifying the button color style with the class attribute like class="mblColorBlue" is no longer supported. Use defaultColor="mblColorBlue" instead.
  • Specifying a DOM Button with the class attribute like class="mblDomButtonWhitePlus" is no longer supported. Use icon="mblDomButtonWhitePlus" instead.
  • select() and deselect() are no longer supported. Use set("selected", boolean) instead.
  • dojox/mobile/parser no longer accepts array-type attributes like:

    .. html ::
    
      <div data-dojo-type="..." labels="['A','B','C','D','E']"></div>
    

    Instead, you should specify array-type attributes as follows:

    .. html ::
    
      <div data-dojo-type="..." labels="A,B,C,D,E"></div>
    

    This is the same format dojo/parser accepts.