Skip to content

Instantly share code, notes, and snippets.

@thejefflarson
Created September 18, 2010 03:23
Show Gist options
  • Save thejefflarson/585300 to your computer and use it in GitHub Desktop.
Save thejefflarson/585300 to your computer and use it in GitHub Desktop.
// The primary function of a **Model** is to manipulate and query data. For example filtering
// an array-type object should happen in a subclass of Model. Another great candidate
// for a **Model** is any object that requires an external resource such as an ajax call.
//
// Basically, any long running or long blocking operation should happen in a model.
//
// **Models** are bindable as well, so you can subscribe to notifications by calling
// `bind` with a callback and an event to subscribe to to recieve events in another object.
//
// **Models** are usually encapsulated in **Views** and rarely, if ever, stand alone.
propublica.Model = Base.extend({
// The **init** method copies the passed in attributes to the instance's built in
// **_attrs** object.
MODEL_CHANGED : "changed",
init : function(attrs){
this._attrs = this._attrs || {};
_.extend(this._attrs, attrs);
this.id = _.uniqueId(this.name || "");
},
// Access an attribute by key.
read : function(key){
return this._attrs[key] || null;
},
// Set an attribute by key.
write : function(key, attr){
var oldAttr = this._attrs[key];
this._attrs[key] = attr;
this._onchange(oldAttr);
return oldAttr;
},
// delete an attribute by key.
remove : function(key){
var oldAttr = this._attrs[key];
delete this._attrs[key];
this._onchange(oldAttr);
return oldAttr;
},
// The **copy** method returns a copy of the current **Model** with the instance's
// attributes filled in.
copy : function(){
return new (this.init)(this._attrs);
},
_onchange : function(oldAttr){
if(this.MODEL_CHANGED) this.fire(this.MODEL_CHANGED, this.id, oldAttr);
},
bind : function(e, cb){
var callbacks = (this._callbacks = this._callbacks || {});
var list = (callbacks[e] = callbacks[e] || []);
list.push(cb);
},
unbind : function(e, cb){
if(!(this._callbacks && this._callbacks[e])) return;
var list = this._callbacks[e];
for(var i = 0; i < list.length; i++){
if(list[i] === cb) {
list.splice(i, 1);
break;
}
}
},
unbindAll : function(){
delete this._callbacks();
},
fire : function(e){
if(!this._callbacks) return;
var list = this._callbacks[e];
if(!list) return;
for(var i = 0; i < list.length; i++) list[i].apply(this, arguments);
}
});
/// subscribing to events
var T = new propublica.Model();
T.on(T.MODEL_CHANGED, function(){ console.log("event fired"); });
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment