marionette-rails 1.0.0.beta6 → 1.0.0.rc1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data/vendor/assets/javascripts/backbone.marionette.js +266 -103
- metadata +1 -1
@@ -1,5 +1,5 @@
|
|
1
1
|
/*!
|
2
|
-
* Backbone.Marionette, v1.0.0-
|
2
|
+
* Backbone.Marionette, v1.0.0-rc1
|
3
3
|
* Copyright (c)2012 Derick Bailey, Muted Solutions, LLC.
|
4
4
|
* Distributed under MIT license
|
5
5
|
* http://github.com/marionettejs/backbone.marionette
|
@@ -12,7 +12,7 @@
|
|
12
12
|
* Includes EventBinder
|
13
13
|
* https://github.com/marionettejs/backbone.eventbinder/
|
14
14
|
*/
|
15
|
-
// Backbone.BabySitter, v0.0.
|
15
|
+
// Backbone.BabySitter, v0.0.4
|
16
16
|
// Copyright (c)2012 Derick Bailey, Muted Solutions, LLC.
|
17
17
|
// Distributed under MIT license
|
18
18
|
// http://github.com/marionettejs/backbone.babysitter
|
@@ -27,12 +27,14 @@ Backbone.ChildViewContainer = (function(Backbone, _){
|
|
27
27
|
// Container Constructor
|
28
28
|
// ---------------------
|
29
29
|
|
30
|
-
var Container = function(
|
30
|
+
var Container = function(initialViews){
|
31
31
|
this._views = {};
|
32
32
|
this._indexByModel = {};
|
33
33
|
this._indexByCollection = {};
|
34
34
|
this._indexByCustom = {};
|
35
35
|
this._updateLength();
|
36
|
+
|
37
|
+
this._addInitialViews(initialViews);
|
36
38
|
};
|
37
39
|
|
38
40
|
// Container Methods
|
@@ -151,18 +153,35 @@ Backbone.ChildViewContainer = (function(Backbone, _){
|
|
151
153
|
// time, like `function.apply`.
|
152
154
|
apply: function(method, args){
|
153
155
|
var view;
|
156
|
+
|
157
|
+
// fix for IE < 9
|
158
|
+
args = args || [];
|
159
|
+
|
154
160
|
_.each(this._views, function(view, key){
|
155
161
|
if (_.isFunction(view[method])){
|
156
162
|
view[method].apply(view, args);
|
157
163
|
}
|
158
164
|
});
|
165
|
+
|
159
166
|
},
|
160
167
|
|
161
168
|
// Update the `.length` attribute on this container
|
162
169
|
_updateLength: function(){
|
163
170
|
this.length = _.size(this._views);
|
164
|
-
}
|
171
|
+
},
|
172
|
+
|
173
|
+
// set up an initial list of views
|
174
|
+
_addInitialViews: function(views){
|
175
|
+
if (!views){ return; }
|
176
|
+
|
177
|
+
var view, i,
|
178
|
+
length = views.length;
|
165
179
|
|
180
|
+
for (i=0; i<length; i++){
|
181
|
+
view = views[i];
|
182
|
+
this.add(view);
|
183
|
+
}
|
184
|
+
}
|
166
185
|
});
|
167
186
|
|
168
187
|
// Borrowing this code from Backbone.Collection:
|
@@ -173,7 +192,7 @@ Backbone.ChildViewContainer = (function(Backbone, _){
|
|
173
192
|
var methods = ['forEach', 'each', 'map', 'find', 'detect', 'filter',
|
174
193
|
'select', 'reject', 'every', 'all', 'some', 'any', 'include',
|
175
194
|
'contains', 'invoke', 'toArray', 'first', 'initial', 'rest',
|
176
|
-
'last', 'without', 'isEmpty'];
|
195
|
+
'last', 'without', 'isEmpty', 'pluck'];
|
177
196
|
|
178
197
|
_.each(methods, function(method) {
|
179
198
|
Container.prototype[method] = function() {
|
@@ -187,7 +206,7 @@ Backbone.ChildViewContainer = (function(Backbone, _){
|
|
187
206
|
return Container;
|
188
207
|
})(Backbone, _);
|
189
208
|
|
190
|
-
// Backbone.EventBinder,
|
209
|
+
// Backbone.EventBinder, v1.0.2
|
191
210
|
// Copyright (c)2012 Derick Bailey, Muted Solutions, LLC.
|
192
211
|
// Distributed under MIT license
|
193
212
|
// http://github.com/marionettejs/backbone.eventbinder
|
@@ -257,6 +276,10 @@ Backbone.EventBinder = (function(Backbone, _){
|
|
257
276
|
// Use whatever best logic necessary to determine the type
|
258
277
|
// of the supplied object
|
259
278
|
function getHandlerForObject(obj) {
|
279
|
+
if (_.isUndefined(obj) || _.isNull(obj)) {
|
280
|
+
throw new Error("Can't bindTo undefined");
|
281
|
+
}
|
282
|
+
|
260
283
|
if (obj.jquery) { return handlerMap.jquery; }
|
261
284
|
|
262
285
|
return handlerMap["default"];
|
@@ -280,7 +303,8 @@ Backbone.EventBinder = (function(Backbone, _){
|
|
280
303
|
var obj = arguments[0];
|
281
304
|
var handlers = getHandlerForObject(obj);
|
282
305
|
|
283
|
-
var
|
306
|
+
var args = Array.prototype.slice.apply(arguments);
|
307
|
+
var binding = handlers.bindTo.apply(this, args);
|
284
308
|
|
285
309
|
this._eventBindings.push(binding);
|
286
310
|
|
@@ -290,7 +314,9 @@ Backbone.EventBinder = (function(Backbone, _){
|
|
290
314
|
// Unbind from a single binding object. Binding objects are
|
291
315
|
// returned from the `bindTo` method call.
|
292
316
|
unbindFrom: function(binding) {
|
293
|
-
|
317
|
+
var args = Array.prototype.slice.apply(arguments);
|
318
|
+
handlerMap[binding.type].unbindFrom.apply(this, args);
|
319
|
+
|
294
320
|
this._eventBindings = _.reject(this._eventBindings, function(bind){return bind === binding;});
|
295
321
|
},
|
296
322
|
|
@@ -306,7 +332,7 @@ Backbone.EventBinder = (function(Backbone, _){
|
|
306
332
|
return EventBinder;
|
307
333
|
})(Backbone, _);
|
308
334
|
|
309
|
-
// Backbone.Wreqr, v0.
|
335
|
+
// Backbone.Wreqr, v0.1.0
|
310
336
|
// Copyright (c)2012 Derick Bailey, Muted Solutions, LLC.
|
311
337
|
// Distributed under MIT license
|
312
338
|
// http://github.com/marionettejs/backbone.wreqr
|
@@ -314,9 +340,16 @@ Backbone.Wreqr = (function(Backbone, Marionette, _){
|
|
314
340
|
"option strict";
|
315
341
|
var Wreqr = {};
|
316
342
|
|
343
|
+
// Handlers
|
344
|
+
// --------
|
345
|
+
// A registry of functions to call, given a name
|
346
|
+
|
317
347
|
Wreqr.Handlers = (function(Backbone, _){
|
318
348
|
"option strict";
|
319
349
|
|
350
|
+
// Constructor
|
351
|
+
// -----------
|
352
|
+
|
320
353
|
var Handlers = function(){
|
321
354
|
"use strict";
|
322
355
|
this._handlers = {};
|
@@ -324,7 +357,13 @@ Backbone.Wreqr = (function(Backbone, Marionette, _){
|
|
324
357
|
|
325
358
|
Handlers.extend = Backbone.Model.extend;
|
326
359
|
|
360
|
+
// Instance Members
|
361
|
+
// ----------------
|
362
|
+
|
327
363
|
_.extend(Handlers.prototype, {
|
364
|
+
|
365
|
+
// Add a handler for the given name, with an
|
366
|
+
// optional context to run the handler within
|
328
367
|
addHandler: function(name, handler, context){
|
329
368
|
var config = {
|
330
369
|
callback: handler,
|
@@ -334,6 +373,9 @@ Backbone.Wreqr = (function(Backbone, Marionette, _){
|
|
334
373
|
this._handlers[name] = config;
|
335
374
|
},
|
336
375
|
|
376
|
+
// Get the currently registered handler for
|
377
|
+
// the specified name. Throws an exception if
|
378
|
+
// no handler is found.
|
337
379
|
getHandler: function(name){
|
338
380
|
var config = this._handlers[name];
|
339
381
|
|
@@ -342,14 +384,17 @@ Backbone.Wreqr = (function(Backbone, Marionette, _){
|
|
342
384
|
}
|
343
385
|
|
344
386
|
return function(){
|
345
|
-
|
387
|
+
var args = Array.prototype.slice.apply(arguments);
|
388
|
+
return config.callback.apply(config.context, args);
|
346
389
|
};
|
347
390
|
},
|
348
391
|
|
392
|
+
// Remove a handler for the specified name
|
349
393
|
removeHandler: function(name){
|
350
394
|
delete this._handlers[name];
|
351
395
|
},
|
352
396
|
|
397
|
+
// Remove all handlers from this registry
|
353
398
|
removeAllHandlers: function(){
|
354
399
|
this._handlers = {};
|
355
400
|
}
|
@@ -367,8 +412,11 @@ Backbone.Wreqr = (function(Backbone, Marionette, _){
|
|
367
412
|
"option strict";
|
368
413
|
|
369
414
|
return Wreqr.Handlers.extend({
|
370
|
-
execute: function(
|
371
|
-
|
415
|
+
execute: function(){
|
416
|
+
var name = arguments[0];
|
417
|
+
var args = Array.prototype.slice.call(arguments, 1);
|
418
|
+
|
419
|
+
this.getHandler(name).apply(this, args);
|
372
420
|
}
|
373
421
|
});
|
374
422
|
|
@@ -383,8 +431,11 @@ Backbone.Wreqr = (function(Backbone, Marionette, _){
|
|
383
431
|
"option strict";
|
384
432
|
|
385
433
|
return Wreqr.Handlers.extend({
|
386
|
-
request: function(
|
387
|
-
|
434
|
+
request: function(){
|
435
|
+
var name = arguments[0];
|
436
|
+
var args = Array.prototype.slice.call(arguments, 1);
|
437
|
+
|
438
|
+
return this.getHandler(name).apply(this, args);
|
388
439
|
}
|
389
440
|
});
|
390
441
|
|
@@ -513,7 +564,7 @@ Marionette.triggerMethod = function(){
|
|
513
564
|
methodName += capLetter + segment.slice(1);
|
514
565
|
}
|
515
566
|
|
516
|
-
this.trigger.apply(this,
|
567
|
+
this.trigger.apply(this, args);
|
517
568
|
|
518
569
|
if (_.isFunction(this[methodName])){
|
519
570
|
args.shift();
|
@@ -526,17 +577,7 @@ Marionette.triggerMethod = function(){
|
|
526
577
|
// -----------
|
527
578
|
// Import the event binder from it's new home
|
528
579
|
// https://github.com/marionettejs/backbone.eventbinder
|
529
|
-
Marionette.EventBinder = Backbone.EventBinder.extend(
|
530
|
-
|
531
|
-
augment: function(target){
|
532
|
-
var eventBinder = new Marionette.EventBinder();
|
533
|
-
target.eventBinder = eventBinder;
|
534
|
-
target.bindTo = _.bind(eventBinder.bindTo, eventBinder);
|
535
|
-
target.unbindFrom = _.bind(eventBinder.unbindFrom, eventBinder);
|
536
|
-
target.unbindAll = _.bind(eventBinder.unbindAll, eventBinder);
|
537
|
-
}
|
538
|
-
|
539
|
-
});
|
580
|
+
Marionette.EventBinder = Backbone.EventBinder.extend();
|
540
581
|
|
541
582
|
// Add the EventBinder methods to the view directly,
|
542
583
|
// but keep them bound to the EventBinder instance so they work properly.
|
@@ -547,7 +588,15 @@ Marionette.EventBinder = Backbone.EventBinder.extend({
|
|
547
588
|
Marionette.addEventBinder = function(target){
|
548
589
|
var eventBinder = new Marionette.EventBinder();
|
549
590
|
target.eventBinder = eventBinder;
|
550
|
-
|
591
|
+
|
592
|
+
target.bindTo = function(source, event, callback, context){
|
593
|
+
// check the context of the bindTo and set it to the object
|
594
|
+
// that is having the eventBinder attached to it, if no context
|
595
|
+
// has been specified in the .bindTo call
|
596
|
+
context = context || target;
|
597
|
+
eventBinder.bindTo(source, event, callback, context);
|
598
|
+
};
|
599
|
+
|
551
600
|
target.unbindFrom = _.bind(eventBinder.unbindFrom, eventBinder);
|
552
601
|
target.unbindAll = _.bind(eventBinder.unbindAll, eventBinder);
|
553
602
|
};
|
@@ -563,11 +612,70 @@ Marionette.EventAggregator = Backbone.Wreqr.EventAggregator.extend({
|
|
563
612
|
|
564
613
|
constructor: function(){
|
565
614
|
Marionette.addEventBinder(this);
|
566
|
-
|
615
|
+
|
616
|
+
var args = Array.prototype.slice.apply(arguments);
|
617
|
+
Backbone.Wreqr.EventAggregator.prototype.constructor.apply(this, args);
|
567
618
|
}
|
568
619
|
|
569
620
|
});
|
570
621
|
|
622
|
+
// Marionette.bindEntityEvents
|
623
|
+
// ---------------------------
|
624
|
+
//
|
625
|
+
// This method is used to bind a backbone "entity" (collection/model)
|
626
|
+
// to methods on a target object.
|
627
|
+
//
|
628
|
+
// The first paremter, `target`, must have a `bindTo` method from the
|
629
|
+
// EventBinder object.
|
630
|
+
//
|
631
|
+
// The second parameter is the entity (Backbone.Model or Backbone.Collection)
|
632
|
+
// to bind the events from.
|
633
|
+
//
|
634
|
+
// The third parameter is a hash of { "event:name": "eventHandler" }
|
635
|
+
// configuration. Multiple handlers can be separated by a space. A
|
636
|
+
// function can be supplied instead of a string handler name.
|
637
|
+
Marionette.bindEntityEvents = (function(){
|
638
|
+
|
639
|
+
// Bind the event to handlers specified as a string of
|
640
|
+
// handler names on the target object
|
641
|
+
function bindFromStrings(target, entity, evt, methods){
|
642
|
+
var methodNames = methods.split(/\s+/);
|
643
|
+
|
644
|
+
_.each(methodNames,function(methodName) {
|
645
|
+
|
646
|
+
var method = target[methodName];
|
647
|
+
if(!method) {
|
648
|
+
throw new Error("Method '"+ methodName +"' was configured as an event handler, but does not exist.");
|
649
|
+
}
|
650
|
+
|
651
|
+
target.bindTo(entity, evt, method, target);
|
652
|
+
});
|
653
|
+
}
|
654
|
+
|
655
|
+
// Bind the event to a supplied callback function
|
656
|
+
function bindToFunction(target, entity, evt, method){
|
657
|
+
target.bindTo(entity, evt, method, target);
|
658
|
+
}
|
659
|
+
|
660
|
+
// Export the bindEntityEvents method
|
661
|
+
return function(target, entity, bindings){
|
662
|
+
if (!entity || !bindings) { return; }
|
663
|
+
|
664
|
+
_.each(bindings, function(methods, evt){
|
665
|
+
|
666
|
+
// allow for a function as the handler,
|
667
|
+
// or a list of event names as a string
|
668
|
+
if (_.isFunction(methods)){
|
669
|
+
bindToFunction(target, entity, evt, methods);
|
670
|
+
} else {
|
671
|
+
bindFromStrings(target, entity, evt, methods);
|
672
|
+
}
|
673
|
+
|
674
|
+
});
|
675
|
+
};
|
676
|
+
})();
|
677
|
+
|
678
|
+
|
571
679
|
// Callbacks
|
572
680
|
// ---------
|
573
681
|
|
@@ -653,11 +761,12 @@ _.extend(Marionette.TemplateCache, {
|
|
653
761
|
// `clear("#t1", "#t2", "...")`
|
654
762
|
clear: function(){
|
655
763
|
var i;
|
656
|
-
var
|
764
|
+
var args = Array.prototype.slice.apply(arguments);
|
765
|
+
var length = args.length;
|
657
766
|
|
658
767
|
if (length > 0){
|
659
768
|
for(i=0; i<length; i++){
|
660
|
-
delete this.templateCaches[
|
769
|
+
delete this.templateCaches[args[i]];
|
661
770
|
}
|
662
771
|
} else {
|
663
772
|
this.templateCaches = {};
|
@@ -783,7 +892,8 @@ Marionette.Region = function(options){
|
|
783
892
|
}
|
784
893
|
|
785
894
|
if (this.initialize){
|
786
|
-
|
895
|
+
var args = Array.prototype.slice.apply(arguments);
|
896
|
+
this.initialize.apply(this, args);
|
787
897
|
}
|
788
898
|
};
|
789
899
|
|
@@ -940,10 +1050,11 @@ Marionette.View = Backbone.View.extend({
|
|
940
1050
|
_.bindAll(this, "render");
|
941
1051
|
Marionette.addEventBinder(this);
|
942
1052
|
|
943
|
-
|
1053
|
+
var args = Array.prototype.slice.apply(arguments);
|
1054
|
+
Backbone.View.prototype.constructor.apply(this, args);
|
944
1055
|
|
945
|
-
|
946
|
-
|
1056
|
+
Marionette.bindEntityEvents(this, this.model, Marionette.getOption(this, "modelEvents"));
|
1057
|
+
Marionette.bindEntityEvents(this, this.collection, Marionette.getOption(this, "collectionEvents"));
|
947
1058
|
|
948
1059
|
this.bindTo(this, "show", this.onShowCalled, this);
|
949
1060
|
},
|
@@ -1023,13 +1134,17 @@ Marionette.View = Backbone.View.extend({
|
|
1023
1134
|
close: function(){
|
1024
1135
|
if (this.isClosed) { return; }
|
1025
1136
|
|
1026
|
-
this.triggerMethod("before:close");
|
1137
|
+
var shouldClose = this.triggerMethod("before:close");
|
1138
|
+
if (shouldClose === false){
|
1139
|
+
return;
|
1140
|
+
}
|
1027
1141
|
|
1028
1142
|
this.remove();
|
1029
|
-
this.unbindAll();
|
1030
1143
|
|
1031
1144
|
this.triggerMethod("close");
|
1032
1145
|
this.isClosed = true;
|
1146
|
+
|
1147
|
+
this.unbindAll();
|
1033
1148
|
},
|
1034
1149
|
|
1035
1150
|
// This method binds the elements specified in the "ui" hash inside the view's code with
|
@@ -1051,22 +1166,6 @@ Marionette.View = Backbone.View.extend({
|
|
1051
1166
|
var selector = that.uiBindings[key];
|
1052
1167
|
that.ui[key] = that.$(selector);
|
1053
1168
|
});
|
1054
|
-
},
|
1055
|
-
|
1056
|
-
// This method is used to bind a backbone "entity" (collection/model) to methods on the view.
|
1057
|
-
bindBackboneEntityTo: function(entity, bindings){
|
1058
|
-
if (!entity || !bindings) { return; }
|
1059
|
-
|
1060
|
-
var view = this;
|
1061
|
-
_.each(bindings, function(methodName, evt){
|
1062
|
-
|
1063
|
-
var method = view[methodName];
|
1064
|
-
if(!method) {
|
1065
|
-
throw new Error("View method '"+ methodName +"' was configured as an event handler, but does not exist.");
|
1066
|
-
}
|
1067
|
-
|
1068
|
-
view.bindTo(entity, evt, method, view);
|
1069
|
-
});
|
1070
1169
|
}
|
1071
1170
|
});
|
1072
1171
|
|
@@ -1078,11 +1177,35 @@ Marionette.View = Backbone.View.extend({
|
|
1078
1177
|
// and calling several methods on extended views, such as `onRender`.
|
1079
1178
|
Marionette.ItemView = Marionette.View.extend({
|
1080
1179
|
constructor: function(){
|
1081
|
-
|
1180
|
+
var args = Array.prototype.slice.apply(arguments);
|
1181
|
+
Marionette.View.prototype.constructor.apply(this, args);
|
1082
1182
|
|
1083
1183
|
if (this.initialEvents){
|
1084
1184
|
this.initialEvents();
|
1085
1185
|
}
|
1186
|
+
|
1187
|
+
this.bindTo(this, "show", this._handleShow, this);
|
1188
|
+
this.bindTo(this, "render", this._handleRender, this);
|
1189
|
+
},
|
1190
|
+
|
1191
|
+
// internal event handler to track when the view has been rendered
|
1192
|
+
_handleShow: function(){
|
1193
|
+
this._isShown = true;
|
1194
|
+
this.triggerDOMRefresh();
|
1195
|
+
},
|
1196
|
+
|
1197
|
+
// internal event handler to track when the view has been shown in the DOM,
|
1198
|
+
// using a Marionette.Region (or by other means of triggering "show")
|
1199
|
+
_handleRender: function(){
|
1200
|
+
this._isRendered = true;
|
1201
|
+
this.triggerDOMRefresh();
|
1202
|
+
},
|
1203
|
+
|
1204
|
+
// Trigger the "dom:refresh" event and corresponding "onDomRefresh" method
|
1205
|
+
triggerDOMRefresh: function(){
|
1206
|
+
if (this._isShown && this._isRendered){
|
1207
|
+
this.triggerMethod("dom:refresh");
|
1208
|
+
}
|
1086
1209
|
},
|
1087
1210
|
|
1088
1211
|
// Serialize the model or collection for the view. If a model is
|
@@ -1135,7 +1258,10 @@ Marionette.ItemView = Marionette.View.extend({
|
|
1135
1258
|
if (this.isClosed){ return; }
|
1136
1259
|
|
1137
1260
|
this.triggerMethod('item:before:close');
|
1138
|
-
|
1261
|
+
|
1262
|
+
var args = Array.prototype.slice.apply(arguments);
|
1263
|
+
Marionette.View.prototype.close.apply(this, args);
|
1264
|
+
|
1139
1265
|
this.triggerMethod('item:closed');
|
1140
1266
|
}
|
1141
1267
|
});
|
@@ -1146,16 +1272,19 @@ Marionette.ItemView = Marionette.View.extend({
|
|
1146
1272
|
// A view that iterates over a Backbone.Collection
|
1147
1273
|
// and renders an individual ItemView for each model.
|
1148
1274
|
Marionette.CollectionView = Marionette.View.extend({
|
1275
|
+
// used as the prefix for item view events
|
1276
|
+
// that are forwarded through the collectionview
|
1277
|
+
itemViewEventPrefix: "itemview",
|
1278
|
+
|
1279
|
+
// constructor
|
1149
1280
|
constructor: function(options){
|
1150
1281
|
this.initChildViewStorage();
|
1151
1282
|
|
1152
|
-
|
1283
|
+
var args = Array.prototype.slice.apply(arguments);
|
1284
|
+
Marionette.View.prototype.constructor.apply(this, args);
|
1285
|
+
|
1153
1286
|
this.initialEvents();
|
1154
1287
|
this.onShowCallbacks = new Marionette.Callbacks();
|
1155
|
-
|
1156
|
-
if (options && options.itemViewOptions) {
|
1157
|
-
this.itemViewOptions = options.itemViewOptions;
|
1158
|
-
}
|
1159
1288
|
},
|
1160
1289
|
|
1161
1290
|
// Configured the initial events that the collection view
|
@@ -1279,45 +1408,54 @@ Marionette.CollectionView = Marionette.View.extend({
|
|
1279
1408
|
var that = this;
|
1280
1409
|
|
1281
1410
|
// get the itemViewOptions if any were specified
|
1282
|
-
var itemViewOptions;
|
1283
|
-
if (_.isFunction(
|
1284
|
-
itemViewOptions =
|
1285
|
-
} else {
|
1286
|
-
itemViewOptions = this.itemViewOptions;
|
1411
|
+
var itemViewOptions = Marionette.getOption(this, "itemViewOptions");
|
1412
|
+
if (_.isFunction(itemViewOptions)){
|
1413
|
+
itemViewOptions = itemViewOptions.call(this, item);
|
1287
1414
|
}
|
1288
1415
|
|
1289
1416
|
// build the view
|
1290
1417
|
var view = this.buildItemView(item, ItemView, itemViewOptions);
|
1418
|
+
|
1419
|
+
// set up the child view event forwarding
|
1420
|
+
this.addChildViewEventForwarding(view);
|
1291
1421
|
|
1292
1422
|
// Store the child view itself so we can properly
|
1293
1423
|
// remove and/or close it later
|
1294
1424
|
this.children.add(view);
|
1425
|
+
|
1426
|
+
// Render it and show it
|
1427
|
+
var renderResult = this.renderItemView(view, index);
|
1428
|
+
|
1429
|
+
// let the world know this view was added
|
1295
1430
|
this.triggerMethod("item:added", view);
|
1296
1431
|
|
1432
|
+
// call onShow for child item views
|
1433
|
+
if (view.onShow){
|
1434
|
+
this.onShowCallbacks.add(view.onShow, view);
|
1435
|
+
}
|
1436
|
+
|
1437
|
+
return renderResult;
|
1438
|
+
},
|
1439
|
+
|
1440
|
+
// Set up the child view event forwarding. Uses an "itemview:"
|
1441
|
+
// prefix in front of all forwarded events.
|
1442
|
+
addChildViewEventForwarding: function(view){
|
1443
|
+
var prefix = Marionette.getOption(this, "itemViewEventPrefix");
|
1444
|
+
|
1297
1445
|
// Forward all child item view events through the parent,
|
1298
1446
|
// prepending "itemview:" to the event name
|
1299
1447
|
var childBinding = this.bindTo(view, "all", function(){
|
1300
1448
|
var args = slice.call(arguments);
|
1301
|
-
args[0] = "
|
1449
|
+
args[0] = prefix + ":" + args[0];
|
1302
1450
|
args.splice(1, 0, view);
|
1303
1451
|
|
1304
|
-
|
1305
|
-
});
|
1452
|
+
this.triggerMethod.apply(this, args);
|
1453
|
+
}, this);
|
1306
1454
|
|
1307
1455
|
// Store all child event bindings so we can unbind
|
1308
1456
|
// them when removing / closing the child view
|
1309
|
-
this.
|
1310
|
-
this.
|
1311
|
-
|
1312
|
-
// Render it and show it
|
1313
|
-
var renderResult = this.renderItemView(view, index);
|
1314
|
-
|
1315
|
-
// call onShow for child item views
|
1316
|
-
if (view.onShow){
|
1317
|
-
this.onShowCallbacks.add(view.onShow, view);
|
1318
|
-
}
|
1319
|
-
|
1320
|
-
return renderResult;
|
1457
|
+
this._childBindings = this._childBindings || {};
|
1458
|
+
this._childBindings[view.cid] = childBinding;
|
1321
1459
|
},
|
1322
1460
|
|
1323
1461
|
// render the item view
|
@@ -1338,10 +1476,10 @@ Marionette.CollectionView = Marionette.View.extend({
|
|
1338
1476
|
var view = this.children.findByModel(item);
|
1339
1477
|
|
1340
1478
|
if (view){
|
1341
|
-
var childBinding = this.
|
1479
|
+
var childBinding = this._childBindings[view.cid];
|
1342
1480
|
if (childBinding) {
|
1343
1481
|
this.unbindFrom(childBinding);
|
1344
|
-
delete this.
|
1482
|
+
delete this._childBindings[view.cid];
|
1345
1483
|
}
|
1346
1484
|
|
1347
1485
|
if (view.close){
|
@@ -1379,7 +1517,9 @@ Marionette.CollectionView = Marionette.View.extend({
|
|
1379
1517
|
this.triggerMethod("collection:before:close");
|
1380
1518
|
this.closeChildren();
|
1381
1519
|
this.triggerMethod("collection:closed");
|
1382
|
-
|
1520
|
+
|
1521
|
+
var args = Array.prototype.slice.apply(arguments);
|
1522
|
+
Marionette.View.prototype.close.apply(this, args);
|
1383
1523
|
},
|
1384
1524
|
|
1385
1525
|
// Close the child views that this collection view
|
@@ -1401,7 +1541,9 @@ Marionette.CollectionView = Marionette.View.extend({
|
|
1401
1541
|
// an item view as `modelView`, for the top leaf
|
1402
1542
|
Marionette.CompositeView = Marionette.CollectionView.extend({
|
1403
1543
|
constructor: function(options){
|
1404
|
-
|
1544
|
+
var args = Array.prototype.slice.apply(arguments);
|
1545
|
+
Marionette.CollectionView.apply(this, args);
|
1546
|
+
|
1405
1547
|
this.itemView = this.getItemView();
|
1406
1548
|
},
|
1407
1549
|
|
@@ -1470,7 +1612,9 @@ Marionette.CompositeView = Marionette.CollectionView.extend({
|
|
1470
1612
|
|
1471
1613
|
// Render the collection for the composite view
|
1472
1614
|
renderCollection: function(){
|
1473
|
-
|
1615
|
+
var args = Array.prototype.slice.apply(arguments);
|
1616
|
+
Marionette.CollectionView.prototype.render.apply(this, args);
|
1617
|
+
|
1474
1618
|
this.triggerMethod("composite:collection:rendered");
|
1475
1619
|
},
|
1476
1620
|
|
@@ -1547,7 +1691,9 @@ Marionette.Layout = Marionette.ItemView.extend({
|
|
1547
1691
|
constructor: function () {
|
1548
1692
|
this._firstRender = true;
|
1549
1693
|
this.initializeRegions();
|
1550
|
-
|
1694
|
+
|
1695
|
+
var args = Array.prototype.slice.apply(arguments);
|
1696
|
+
Backbone.Marionette.ItemView.apply(this, args);
|
1551
1697
|
},
|
1552
1698
|
|
1553
1699
|
// Layout's render will use the existing region objects the
|
@@ -1567,7 +1713,9 @@ Marionette.Layout = Marionette.ItemView.extend({
|
|
1567
1713
|
this.reInitializeRegions();
|
1568
1714
|
}
|
1569
1715
|
|
1570
|
-
var
|
1716
|
+
var args = Array.prototype.slice.apply(arguments);
|
1717
|
+
var result = Marionette.ItemView.prototype.render.apply(this, args);
|
1718
|
+
|
1571
1719
|
return result;
|
1572
1720
|
},
|
1573
1721
|
|
@@ -1577,7 +1725,9 @@ Marionette.Layout = Marionette.ItemView.extend({
|
|
1577
1725
|
|
1578
1726
|
this.closeRegions();
|
1579
1727
|
this.destroyRegions();
|
1580
|
-
|
1728
|
+
|
1729
|
+
var args = Array.prototype.slice.apply(arguments);
|
1730
|
+
Backbone.Marionette.ItemView.prototype.close.apply(this, args);
|
1581
1731
|
},
|
1582
1732
|
|
1583
1733
|
// Initialize the regions that have been defined in a
|
@@ -1662,7 +1812,9 @@ Marionette.Layout = Marionette.ItemView.extend({
|
|
1662
1812
|
Marionette.AppRouter = Backbone.Router.extend({
|
1663
1813
|
|
1664
1814
|
constructor: function(options){
|
1665
|
-
|
1815
|
+
var args = Array.prototype.slice.apply(arguments);
|
1816
|
+
Backbone.Router.prototype.constructor.apply(this, args);
|
1817
|
+
|
1666
1818
|
this.options = options;
|
1667
1819
|
|
1668
1820
|
if (this.appRoutes){
|
@@ -1728,12 +1880,14 @@ Marionette.Application = function(options){
|
|
1728
1880
|
_.extend(Marionette.Application.prototype, Backbone.Events, {
|
1729
1881
|
// Command execution, facilitated by Backbone.Wreqr.Commands
|
1730
1882
|
execute: function(){
|
1731
|
-
|
1883
|
+
var args = Array.prototype.slice.apply(arguments);
|
1884
|
+
this.commands.execute.apply(this.commands, args);
|
1732
1885
|
},
|
1733
1886
|
|
1734
1887
|
// Request/response, facilitated by Backbone.Wreqr.RequestResponse
|
1735
1888
|
request: function(){
|
1736
|
-
|
1889
|
+
var args = Array.prototype.slice.apply(arguments);
|
1890
|
+
return this.reqres.request.apply(this.reqres, args);
|
1737
1891
|
},
|
1738
1892
|
|
1739
1893
|
// Add an initializer that is either run at when the `start`
|
@@ -1808,6 +1962,7 @@ Marionette.Module = function(moduleName, app){
|
|
1808
1962
|
|
1809
1963
|
// extend this module with an event binder
|
1810
1964
|
Marionette.addEventBinder(this);
|
1965
|
+
this.triggerMethod = Marionette.triggerMethod;
|
1811
1966
|
};
|
1812
1967
|
|
1813
1968
|
// Extend the Module prototype with events / bindTo, so that the module
|
@@ -1847,8 +2002,12 @@ _.extend(Marionette.Module.prototype, Backbone.Events, {
|
|
1847
2002
|
});
|
1848
2003
|
|
1849
2004
|
// run the callbacks to "start" the current module
|
2005
|
+
this.triggerMethod("before:start", options);
|
2006
|
+
|
1850
2007
|
this._initializerCallbacks.run(options, this);
|
1851
2008
|
this._isInitialized = true;
|
2009
|
+
|
2010
|
+
this.triggerMethod("start", options);
|
1852
2011
|
},
|
1853
2012
|
|
1854
2013
|
// Stop this module by running its finalizers and then stop all of
|
@@ -1858,6 +2017,8 @@ _.extend(Marionette.Module.prototype, Backbone.Events, {
|
|
1858
2017
|
if (!this._isInitialized){ return; }
|
1859
2018
|
this._isInitialized = false;
|
1860
2019
|
|
2020
|
+
Marionette.triggerMethod.call(this, "before:stop");
|
2021
|
+
|
1861
2022
|
// stop the sub-modules; depth-first, to make sure the
|
1862
2023
|
// sub-modules are stopped / finalized before parents
|
1863
2024
|
_.each(this.submodules, function(mod){ mod.stop(); });
|
@@ -1868,6 +2029,8 @@ _.extend(Marionette.Module.prototype, Backbone.Events, {
|
|
1868
2029
|
// reset the initializers and finalizers
|
1869
2030
|
this._initializerCallbacks.reset();
|
1870
2031
|
this._finalizerCallbacks.reset();
|
2032
|
+
|
2033
|
+
Marionette.triggerMethod.call(this, "stop");
|
1871
2034
|
},
|
1872
2035
|
|
1873
2036
|
// Configure the module with a definition function and any custom args
|
@@ -1883,11 +2046,11 @@ _.extend(Marionette.Module.prototype, Backbone.Events, {
|
|
1883
2046
|
|
1884
2047
|
// build the correct list of arguments for the module definition
|
1885
2048
|
var args = _.flatten([
|
1886
|
-
this,
|
1887
|
-
this.config.app,
|
1888
|
-
Backbone,
|
1889
|
-
Marionette,
|
1890
|
-
$, _,
|
2049
|
+
this,
|
2050
|
+
this.config.app,
|
2051
|
+
Backbone,
|
2052
|
+
Marionette,
|
2053
|
+
$, _,
|
1891
2054
|
customArgs
|
1892
2055
|
]);
|
1893
2056
|
|
@@ -1906,7 +2069,7 @@ _.extend(Marionette.Module.prototype, Backbone.Events, {
|
|
1906
2069
|
// Function level methods to create modules
|
1907
2070
|
_.extend(Marionette.Module, {
|
1908
2071
|
|
1909
|
-
// Create a module, hanging off the app parameter as the parent object.
|
2072
|
+
// Create a module, hanging off the app parameter as the parent object.
|
1910
2073
|
create: function(app, moduleNames, moduleDefinition){
|
1911
2074
|
var that = this;
|
1912
2075
|
var parentModule = app;
|
@@ -1929,7 +2092,7 @@ _.extend(Marionette.Module, {
|
|
1929
2092
|
if (isLastModuleInChain){
|
1930
2093
|
module.config.options = that._getModuleOptions(module, parentModule, moduleDefinition);
|
1931
2094
|
|
1932
|
-
// Only add a module definition and initializer when this is the last
|
2095
|
+
// Only add a module definition and initializer when this is the last
|
1933
2096
|
// module in a "parent.child.grandchild" hierarchy of module names and
|
1934
2097
|
// when the module call has a definition function supplied
|
1935
2098
|
if (module.config.options.hasDefinition){
|
@@ -1953,14 +2116,14 @@ _.extend(Marionette.Module, {
|
|
1953
2116
|
return parentModule;
|
1954
2117
|
},
|
1955
2118
|
|
1956
|
-
// Only add the initializer if it is set to start with parent (the app),
|
2119
|
+
// Only add the initializer if it is set to start with parent (the app),
|
1957
2120
|
// and if it has not yet been added
|
1958
2121
|
_configureStartWithApp: function(app, module){
|
1959
2122
|
// skip this if we have already configured the module to start w/ the app
|
1960
2123
|
if (module.config.startWithAppIsConfigured){
|
1961
2124
|
return;
|
1962
2125
|
}
|
1963
|
-
|
2126
|
+
|
1964
2127
|
// start the module when the app starts
|
1965
2128
|
app.addInitializer(function(options){
|
1966
2129
|
// but only if the module is configured to start w/ parent
|
@@ -1979,7 +2142,7 @@ _.extend(Marionette.Module, {
|
|
1979
2142
|
// Get an existing module of this name if we have one
|
1980
2143
|
var module = parentModule[moduleName];
|
1981
2144
|
|
1982
|
-
if (!module){
|
2145
|
+
if (!module){
|
1983
2146
|
// Create a new module if we don't have one
|
1984
2147
|
module = new Marionette.Module(moduleName, app);
|
1985
2148
|
parentModule[moduleName] = module;
|
@@ -1998,7 +2161,7 @@ _.extend(Marionette.Module, {
|
|
1998
2161
|
}
|
1999
2162
|
|
2000
2163
|
// set up initial options for the module
|
2001
|
-
var options = {
|
2164
|
+
var options = {
|
2002
2165
|
startWithParent: startWithParent,
|
2003
2166
|
hasDefinition: !!moduleDefinition
|
2004
2167
|
};
|
@@ -2013,12 +2176,12 @@ _.extend(Marionette.Module, {
|
|
2013
2176
|
|
2014
2177
|
} else {
|
2015
2178
|
|
2016
|
-
// the definition is an object.
|
2179
|
+
// the definition is an object.
|
2017
2180
|
|
2018
2181
|
// grab the "define" attribute
|
2019
2182
|
options.hasDefinition = !!moduleDefinition.define;
|
2020
2183
|
options.definition = moduleDefinition.define;
|
2021
|
-
|
2184
|
+
|
2022
2185
|
// grab the "startWithParent" attribute if one exists
|
2023
2186
|
if (moduleDefinition.hasOwnProperty("startWithParent")){
|
2024
2187
|
options.startWithParent = moduleDefinition.startWithParent;
|