如何通过backbone.js中的全局变量创建集合?

时间:2017-02-21 11:59:58

标签: javascript backbone.js

我在stackoverflow中得到了许多顾问的帮助,部分问题已经解决,但仍然存在一些问题。

我查阅了答案,我试图解决问题,因为我理解了javascript命名空间模式。

A namespacing pattern to avoid polluting the global namespace.
More details on this namespacing pattern
How do I declare a namespace in JavaScript?

我遇到了成功创建全局变量的问题,但是我没有处理生成的变量。

collecton.js

    var app = app || {};
(function () {
    'use strict';
    var collections = app.Collection = app.Collection || {};

    collections.VideoLists =  Backbone.Collection.extend({
        model: app.Model,
        initialize: function(){
            console.log('load Collection');
        }
    });

    app.Collection = collections.VideoLists;
})();

model.js

var app = app || {};
(function() {
    'use strict';
    var models = app.Model = app.Model || {};

    models.Video = Backbone.Model.extend({
        initialize: function(){
            console.log('model create');
        },
        defaults:{
                 id : "1",
                 url : "/assets/videos/call/MOV01718.mp4",
                 imgSrc : "assets/img/call/1_thumbnail.png",
                 title: "call situation conservation"
        }
    });
  app.Model = new models.Video();
})();

router.js

listRoute: function(id) {
          //generate the collection using the listsection
          var videoList = this.collection;
          var getId = parseInt(id);
            switch (getId) {
              case 1:
                new videoList([
                    {
                      id : "1",
                      url : "/assets/videos/call/MOV01718.mp4",
                      imgSrc : "assets/img/call/1_thumbnail.png",
                      title: "call situation conservation"
                    },
                    {
                      id : "2",
                      url : "/assets/videos/call/MOV01722.mp4",
                      imgSrc : "assets/img/call/2_thumbnail.png",
                      title: "call situation conservation"
                    }
                  ]);
                break;

  //app.router init part
  initialize: function() {
            // create the layout once here
            this.layout = new views.Application({
                el: 'body',
            });
            // create model and collection once here
            this.model = app.Model;
            this.collection = app.Collection;
        }

请参阅下图 enter image description here

我认为这一代人已经做得很好 但我不明白为什么会出现这个错误。

我先尝试过 1.不要使用new function(作为我当前的来源)生成集合 2.将变量videoList创建为Object 3.在变量中存储Collection 4.使用collection.create函数。
   例如,list.create({id:'dasdsad'});

然而,这种尝试最终产生了相同的结果 我该如何解决?

1 个答案:

答案 0 :(得分:5)

命名空间模式的目的是什么?

您滥用命名空间模式。这种情况下的目标是将所有自定义Backbone类构造函数命名为app对象。

为了使所有内容清楚地分开,将所有集合构造函数放入app.Collection对象,app.Model中的模型构造函数等。

如果在创建所有类之后检查app命名空间,它应如下所示:

var app = {
    Collection: {
        VideoList: /* video list constructor */
    },
    Model: {
        Video: /* video model constructor */
    },
    View: {
        /* same thing goes for views */
    }
};

app命名空间不应该 1 包含实例,主要是构造函数。

不要覆盖构造函数引用:

app.Model = new models.Video();

只在您需要一个实例时创建一个实例,并将其保留在所需的范围内。

this.model = new app.Model.Video();
this.collection = app.Collection.VideoList();

实例和构造函数

要真正理解前一点,您需要了解构造函数和实例之间的差异。该概念适用于其他OOP语言,但我会将描述保留在JavaScript语言细节中。

构造函数只是一个函数。来自MDN doc on Object.prototype.constructor

  

所有对象都有constructor属性。

     

[...]

     

以下示例创建一个原型Tree及其对象   类型,theTree

function Tree(name) {
  this.name = name;
}

var theTree = new Tree('Redwood');

如上例所示,要创建实例,请使用new operatorWhat is the 'new' keyword in JavaScript?

  

new运算符创建用户定义的对象类型或的实例   其中一个具有构造函数的内置对象类型。

new constructor[([arguments])]

创建自定义构造函数允许您定义自定义类型(类)。有多种方法可以在JavaScript中创建更复杂的自定义类型,但这是另一种讨论。有关详细信息,请参阅How to “properly” create a custom object in JavaScript?

幸运的是,Backbone提供了一种简单(固定)的方式来定义新类型extend function,即available on all the Backbone's base types

var ModelConstructor = Backbone.Model.extend({ /*...*/ });

var modelInstance = new ModelConstructor();

请注意,myVariable = MyConstructor只会将构造函数的引用传递给myVariable,它不会创建新实例。你仍然可以使用变量作为构造函数。

var myInstance = new myVariable();

订购和依赖

如果您查看代码,您会注意到app.Collection.VideoList类使用app.Model.Video作为model属性的值。

这意味着app.Collection.VideoList取决于app.Model.Video类的可用性。因此,应该在模型文件之后将集合文件插入到文档中。

与你联系的the other answer of mine一样:

<script src="js/models/todo.js"></script><!-- no dependencies -->
<script src="js/collections/todos.js"></script><!-- depends on the model -->
<script src="js/views/todo-view.js"></script><!-- depends on the collection and the model -->
<script src="js/views/app-view.js"></script><!-- depends on the todo-view -->
<script src="js/routers/router.js"></script><!-- depends on the app view -->
<script src="js/app.js"></script><!-- depends on the router -->

1。 app命名空间对象可以包含对象的实例,如果您想在所有应用程序之间共享它,如单例,命名空间全局或服务。