Dojo AMD: не могу позвонить в функцию внутри требуемого

StackOverflow https://stackoverflow.com//questions/9626821

  •  09-12-2019
  •  | 
  •  

Вопрос

Я действительно новичок в додзё, но, как я начал разрабатывать новое приложение с версией Dojo 1.7.2, я также хотел использовать новый синтаксис AMD для функций. К сожалению, я, кажется, не понимаю этого. :-(

Что меня раздражает, в том, что я не могу просто назвать любую функцию, которая находится внутри «требует» -блок. Например у меня есть страница, которая на открытии создает динамическую таблицу с несколькими виджетами в каждой строке. Тогда у меня есть кнопка, которая добавляет одну пустую строку каждый раз нажатую.

без синтаксиса AMD Было бы легко:

- Поместите все мои «dojo.require ()» в голову - а затем создать кучу своих собственных функций для создания таблицы и виджетов - Функция Add Row может легко получить доступ к любым глобальным переменным, моя предыдущая функция заполнена

Но с AMD это так:

Начальная функция создает таблицу и виджеты:

function fillReportTable(repId) {
require(["dojo/dom-construct", "dojo/dom-attr", "dijit/form/FilteringSelect",
"dojo/data/ItemFileReadStore", "dijit/form/ComboBox", "dijit/form/DateTextBox", "dijit/form/Select", "dojo/store/Memory"],
     function (domConstruct, domAttr, FilteringSelect, ItemFileReadStore, ComboBox, DateTextBox, Select, Memory) {
   // a lot of code to create the table, consisting of SEVERAL functions 
   function createNewRow(tbl) { ...} 
   function function1 () {... } 
   function function2 () {... } 
   function function3 () {... } 
}
.

Теперь кнопка «Добавить пустую строку» вызывает свою собственную функцию «addemptyry».

Но в этой функции мне нужно:
- сделать другое требование для каждого модуля Dojo - снова
- Я не могу использовать какие-либо из функций, которые «внутри» «FillReporttable». Например, «CreateNwrow» - функция

 function addEmptyRow() {
require(["dojo/dom-construct", "dojo/dom-attr", "dijit/form/FilteringSelect",
"dojo/data/ItemFileReadStore", "dijit/form/ComboBox", "dijit/form/DateTextBox", "dijit/form/Select", "dojo/store/Memory"],
     function (domConstruct, domAttr, FilteringSelect, ItemFileReadStore, ComboBox, DateTextBox, Select, Memory) {
// a lot of code to create the table, consisting of SEVERAL functions
}
.

Это все, кажется, намного сложно с AMD.
Или я упускаю что-то очевидное здесь?
С AMD, если вы разделяете свой код в много маленьких функций, вы делаете «требуют» внутри каждой функции снова и снова? Или вы помещаете все функции внутри одного «требуют» с полным списком?

Если вы сделаете это во втором пути, как вы можете вызвать эти функции из событий виджета?

Это было полезно?

Решение

The easiest way would be to define your own module. Take a look at this tutorial first:

http://dojotoolkit.org/documentation/tutorials/1.7/modules/

Now define your own module, e.g. "./js/mymodules/mymodule.js" (relative to HTML page):

define([
    "dojo/dom-construct",
    "dojo/dom-attr",
    "dijit/form/FilteringSelect",
    "dojo/data/ItemFileReadStore",
    "dijit/form/ComboBox",
    "dijit/form/DateTextBox",
    "dijit/form/Select",
    "dojo/store/Memory"
], function (domConstruct, domAttr, FilteringSelect, ItemFileReadStore, ComboBox, DateTextBox, Select, Memory) {

    function fillReportTable(repId) {
       // a lot of code to create the table, consisting of SEVERAL functions 
       function createNewRow(tbl) { ...} 
       function function1 () {... } 
       function function2 () {... } 
       function function3 () {... } 
    }

    function addEmptyRow() {
       // a lot of code to create the table, consisting of SEVERAL functions
    }

    // Return an object that exposes two functions
    return {
        fillReportTable: fillReportTable,
        addEmptyRow: addEmptyRow
    }

});

And use your module like this:

<html>

<head>

<script>
var dojoConfig = {
    baseUrl: "./js/",
    packages: [
        { name: "dojo", location: "lib/dojo" },
        { name: "dijit", location: "lib/dijit" },
        { name: "dojox", location: "lib/dojox" }
    ]
};
</script>

<script data-dojo-config="async: true" src="js/lib/dojo/dojo.js"></script>

</head>

...

<script>
require([
    "mymodules/mymodule"
], function (mymodule) {
    mymodule.fillReportTable(...);
    mymodule.addEmptyRow(...);
});
</script>

Другие советы

Try this:

require([...], function() {
    var myFunctions = dojo.getObject('myFunctions', true);
    myFunctions.createNewRow = function(...) {
        ...
    };
});

You can now call your functions from anywhere by using

myFunctions.createNewRow();

If you don't want 'myFunctions', you could do

require([...], function() {
    var createNewRow = function(...) {};

    dojo.setObject('createNewRow', createNewRow);
});

Paul Grime gave you a good example, so I'm just sharing some thoughts.

You don't define all the modules in each function, that's a huge waste of space. Although, even if you try to load a module multiple times, Dojo will only load it once anyway.

This is a simplified module from my latest project, with quite meaningless functionality:

//app module in 'my' folder

define(
[
    'app/elements',
    'dojo/query',
    'dojo/on',
    'dojo/fx',
    'dojo/_base/fx',
    'dojo/dom-construct',
    'dojo/_base/event'

    //and so on.....
], 

function(elements, q, on, fx, baseFx, constr, event)
{   
    return {

        init : function()
        {
            var node = q(elements.loading);
            this.removeNode(node);

            this.addEvents();
        },

        removeNode : function(node)
        {
            node.remove();
        },

        addEvents : function()
        {
            $(elements.buttons).on('click', function(e)
            {
                alert(q(e).attr('id') + ' was clicked!');
            });
        }   
    }
}

Then I get the module by using

define(
[
    'my/app',
], 

function (app) 
{
    app.init();
}
Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top