This repository has been archived on 2023-03-18. You can view files and clone it, but cannot push or open issues or pull requests.
osr-discourse-src/app/assets/javascripts/discourse/helpers/grouped_each.js

133 lines
3.5 KiB
JavaScript

var DiscourseGroupedEach = function(context, path, options) {
var self = this,
normalized = Ember.Handlebars.normalizePath(context, path, options.data);
this.context = context;
this.path = path;
this.options = options;
this.template = options.fn;
this.containingView = options.data.view;
this.normalizedRoot = normalized.root;
this.normalizedPath = normalized.path;
this.content = this.lookupContent();
this.destroyed = false;
this.addContentObservers();
this.addArrayObservers();
this.containingView.on('willClearRender', function() {
self.destroy();
});
};
DiscourseGroupedEach.prototype = {
contentWillChange: function() {
this.removeArrayObservers();
},
contentDidChange: function() {
this.content = this.lookupContent();
this.addArrayObservers();
this.rerenderContainingView();
},
contentArrayWillChange: Ember.K,
contentArrayDidChange: function() {
this.rerenderContainingView();
},
lookupContent: function() {
return Ember.Handlebars.get(this.normalizedRoot, this.normalizedPath, this.options);
},
addArrayObservers: function() {
if (!this.content) { return; }
this.content.addArrayObserver(this, {
willChange: 'contentArrayWillChange',
didChange: 'contentArrayDidChange'
});
},
removeArrayObservers: function() {
if (!this.content) { return; }
this.content.removeArrayObserver(this, {
willChange: 'contentArrayWillChange',
didChange: 'contentArrayDidChange'
});
},
addContentObservers: function() {
Ember.addBeforeObserver(this.normalizedRoot, this.normalizedPath, this, this.contentWillChange);
Ember.addObserver(this.normalizedRoot, this.normalizedPath, this, this.contentDidChange);
},
removeContentObservers: function() {
Ember.removeBeforeObserver(this.normalizedRoot, this.normalizedPath, this.contentWillChange);
Ember.removeObserver(this.normalizedRoot, this.normalizedPath, this.contentDidChange);
},
render: function() {
if (!this.content) { return; }
var content = this.content,
contentLength = Em.get(content, 'length'),
data = this.options.data,
template = this.template,
keyword = this.options.hash.keyword;
data.insideEach = true;
for (var i = 0; i < contentLength; i++) {
var row = content.objectAt(i);
if (keyword) {
data.keywords = data.keywords || {};
data.keywords[keyword] = row;
}
template(row, { data: data });
}
},
rerenderContainingView: function() {
var self = this;
Ember.run.scheduleOnce('render', this, function() {
// It's possible it's been destroyed after we enqueued a re-render call.
if (!self.destroyed) {
self.containingView.rerender();
}
});
},
destroy: function() {
this.removeContentObservers();
if (this.content) {
this.removeArrayObservers();
}
this.destroyed = true;
}
};
Ember.Handlebars.registerHelper('groupedEach', function(path, options) {
if (arguments.length === 4) {
Ember.assert("If you pass more than one argument to the groupedEach helper, it must be in the form #groupedEach foo in bar", arguments[1] === "in");
var keywordName = arguments[0];
options = arguments[3];
path = arguments[2];
if (path === '') { path = "this"; }
options.hash.keyword = keywordName;
}
if (arguments.length === 1) {
options = path;
path = 'this';
}
options.hash.dataSourceBinding = path;
options.data.insideGroup = true;
new DiscourseGroupedEach(this, path, options).render();
});