javascriptextjsdom-eventsextjs4.1

Binding events for more than a single controller in ExtJs


I've assembled a modestly sized application and I am in the process of factoring code to reduce the overall number of maintained lines, as well as performance tuning. The use case that has me posting this question is that I have a button embedded in a menu that invokes (or needs to invoke) a method on a controller that displays a form. This currently is implemented using a direct reference to the specific button control, creating a panel, and putting that panel inside of my viewport.

The question at: ExtJS 4.1 Call One Controller From Another begins to address the issue of best-practices near the end of responses, but doesn't really settle on a base-case that can be reproduced or extended to cover more complex implementations (which is the aim of my question.)

Given the two controllers:

A "main menu" controller.

// controller/Menu.js
Ext.define("App.controller.Menu", {
    extend: "Ext.app.Controller",
    init: function () {
        this.control({
            "viewport > mainmenu > button": function (ctl, evt) {
            }
        });
    }
});

A user account controller

// controller/User.js
Ext.define("App.controller.User", {
    extend: "Ext.app.Controller",
    stores: ["User"],
    views: ["user.Edit", "user.List"],
    init: function () {
    }
});

The Question

What would be the (best) way to implement a crosswise connection between the two controllers to properly delegate the responsibility of responding to a click event on the menu button for "Create a New Account?"

One Possible Solution

Using componentquery I can easily narrow down the focus of the button in the main menu view using a tag property such that the User controller is responding directly to the event:

// controller/User.js
"viewport > mainmenu > button [tag=user.create]": function () {}

An unknown alternative

Or I could possible winnow my way through the object graph to find the reference to the User controller from the Menu controller and invoke it that way.

// controller/Menu.js
// switch on tag case "user.create"
App.controller.User.createUserForm()

The real question

The question that results from all of this is what the "most acceptable" solution is here. One could imagine the use of a third, mediating controller, to "route" requests from controls to controllers but I think that goes against what the remainder of the framework is attempting to do. Using a variation of either of these methods currently works however neither feels completely clean and reliable; or ultimately maintainable long-term (as code gets spread out rather quickly.) Additionally the thought had occurred to us to drop into raw events but we run into the same kind of maintainability issues there.


Solution

  • Some short lines:

    A thing that I don't understand is that Sencha Touch has routing but no eventbus where ExtJS has a event bus but no routing... (and there are more points where the MVC implementation differ) Whatsoever, because I am using ExtJS most of the time I created a custom routing to fill this gap for me. Maybe sencha will add this in version 5.