/*
  knockback.js 0.14.2
  (c) 2011 Kevin Malakoff.
  Knockback.js is freely distributable under the MIT license.
  See the following for full license details:
    https://github.com/kmalakoff/knockback/blob/master/LICENSE
  Dependencies: Knockout.js, Backbone.js, and Underscore.js.
    Optional dependency: Backbone.ModelRef.js.
*/if (!this.ko) {
  throw new Error('Knockback: Dependency alert! Knockout.js must be included before this file');
}
if (!this.Backbone) {
  throw new Error('Knockback: Dependency alert! Backbone.js must be included before this file');
}
if (!this._ || !this._.VERSION) {
  throw new Error('Knockback: Dependency alert! Underscore.js must be included before this file');
}
this.Knockback || (this.Knockback = {});
this.kb || (this.kb = this.Knockback);
Knockback.VERSION = '0.14.2';
Knockback.locale_manager;
Knockback.wrappedObservable = function(instance) {
  if (!instance._kb_observable) {
    throw new Error('Knockback: _kb_observable missing from your instance');
  }
  return instance._kb_observable;
};
Knockback.setToDefault = function(observable) {
  if (observable && observable.setToDefault) {
    return observable.setToDefault();
  }
};
Knockback.vmSetToDefault = function(view_model) {
  var key, observable, _results;
  _results = [];
  for (key in view_model) {
    observable = view_model[key];
    _results.push(kb.setToDefault(observable));
  }
  return _results;
};
Knockback.vmRelease = function(view_model) {
  if (view_model instanceof kb.ViewModel_RCBase) {
    view_model.release();
    return;
  }
  return Knockback.vmReleaseObservables(view_model);
};
Knockback.vmReleaseObservables = function(view_model, keys) {
  var key, value, _results;
  _results = [];
  for (key in view_model) {
    value = view_model[key];
    if (!value) {
      continue;
    }
    if (!(ko.isObservable(value) || (value instanceof kb.Observables) || (value instanceof kb.ViewModel_RCBase))) {
      continue;
    }
    if (keys && !_.contains(keys, key)) {
      continue;
    }
    view_model[key] = null;
    _results.push(kb.vmReleaseObservable(value));
  }
  return _results;
};
Knockback.vmReleaseObservable = function(observable) {
  if (!(ko.isObservable(observable) || (observable instanceof kb.Observables) || (observable instanceof kb.ViewModel_RCBase))) {
    return;
  }
  if (observable.destroy) {
    return observable.destroy();
  } else if (observable.dispose) {
    return observable.dispose();
  } else if (observable.release) {
    return observable.release();
  }
};
/*
  knockback_collection_observable.js
  (c) 2011 Kevin Malakoff.
  Knockback.CollectionObservable is freely distributable under the MIT license.
  See the following for full license details:
    https://github.com/kmalakoff/knockback/blob/master/LICENSE
*/
var __bind = function(fn, me){ return function(){ return fn.apply(me, arguments); }; }, __hasProp = Object.prototype.hasOwnProperty, __extends = function(child, parent) {
  for (var key in parent) { if (__hasProp.call(parent, key)) child[key] = parent[key]; }
  function ctor() { this.constructor = child; }
  ctor.prototype = parent.prototype;
  child.prototype = new ctor;
  child.__super__ = parent.prototype;
  return child;
};
if (!this.Knockback) {
  throw new Error('Knockback: Dependency alert! knockback_core.js must be included before this file');
}
Knockback.CollectionObservable = (function() {
  function CollectionObservable(collection, vm_observable_array, options) {
    var defer, event, _i, _j, _len, _len2, _ref, _ref2;
    this.vm_observable_array = vm_observable_array;
    if (options == null) {
      options = {};
    }
    if (!collection) {
      throw new Error('CollectionObservable: collection is missing');
    }
    if (options.hasOwnProperty('view_model')) {
      options.view_model_constructor = options['view_model'];
      delete options['view_model'];
    }
    if (this.vm_observable_array || options.view_model_create || options.view_model_constructor) {
      if (!this.vm_observable_array) {
        throw new Error('CollectionObservable: vm_observable_array is missing');
      }
    }
    if (options.hasOwnProperty('defer')) {
      defer = options.defer;
      delete options['defer'];
    }
    this.options = _.clone(options);
    _.bindAll(this, 'destroy', 'collection', 'sortedIndex', 'sortAttribute', 'viewModelByModel', 'eachViewModel', 'bind', 'unbind', 'trigger');
    _.bindAll(this, '_onGetValue', '_onCollectionReset', '_onCollectionResort', '_onModelAdd', '_onModelRemove', '_onModelChanged');
    this._kb_collection = collection;
    if (this._kb_collection.retain) {
      this._kb_collection.retain();
    }
    this._kb_collection.bind('reset', this._onCollectionReset);
    if (!this.options.sorted_index) {
      this._kb_collection.bind('resort', this._onCollectionResort);
    }
    _ref = ['new', 'add'];
    for (_i = 0, _len = _ref.length; _i < _len; _i++) {
      event = _ref[_i];
      this._kb_collection.bind(event, this._onModelAdd);
    }
    _ref2 = ['remove', 'destroy'];
    for (_j = 0, _len2 = _ref2.length; _j < _len2; _j++) {
      event = _ref2[_j];
      this._kb_collection.bind(event, this._onModelRemove);
    }
    this._kb_collection.bind('change', this._onModelChanged);
    this._kb_value_observable = ko.observableArray([]);
    this._kb_observable = ko.dependentObservable(this._onGetValue);
    this._kb_observable.destroy = this.destroy;
    this._kb_observable.collection = this.collection;
    this._kb_observable.viewModelByModel = this.viewModelByModel;
    this._kb_observable.eachViewModel = this.eachViewModel;
    this._kb_observable.sortedIndex = this.sortedIndex;
    this._kb_observable.sortAttribute = this.sortAttribute;
    this._kb_observable.bind = this.bind;
    this._kb_observable.unbind = this.unbind;
    this._kb_observable.trigger = this.trigger;
    this.sortedIndex(this.options.sorted_index, this.options.sort_attribute, {
      silent: true,
      defer: defer
    });
    return kb.wrappedObservable(this);
  }
  CollectionObservable.prototype.destroy = function() {
    var event, _i, _j, _len, _len2, _ref, _ref2;
    this._clearViewModels();
    this._kb_collection.unbind('reset', this._onCollectionReset);
    if (!this.options.sorted_index) {
      this._kb_collection.unbind('resort', this._onCollectionResort);
    }
    _ref = ['new', 'add'];
    for (_i = 0, _len = _ref.length; _i < _len; _i++) {
      event = _ref[_i];
      this._kb_collection.unbind(event, this._onModelAdd);
    }
    _ref2 = ['remove', 'destroy'];
    for (_j = 0, _len2 = _ref2.length; _j < _len2; _j++) {
      event = _ref2[_j];
      this._kb_collection.unbind(event, this._onModelRemove);
    }
    this._kb_collection.unbind('change', this._onModelChanged);
    if (this._kb_collection.release) {
      this._kb_collection.release();
    }
    this._kb_collection = null;
    this._kb_value_observable = null;
    this._kb_observable.dispose();
    this._kb_observable = null;
    return this.options = null;
  };
  CollectionObservable.prototype.collection = function() {
    this._kb_value_observable();
    return this._kb_collection;
  };
  CollectionObservable.prototype.sortedIndex = function(sorted_index, sort_attribute, options) {
    var _resync;
    if (options == null) {
      options = {};
    }
    if (sorted_index) {
      this.options.sorted_index = sorted_index;
      this.options.sort_attribute = sort_attribute;
    } else if (sort_attribute) {
      this.options.sort_attribute = sort_attribute;
      this.options.sorted_index = this._sortAttributeFn(sort_attribute);
    } else {
      this.options.sort_attribute = null;
      this.options.sorted_index = null;
    }
    _resync = __bind(function() {
      if ((this._kb_collection.models.length === 0) && (this._kb_value_observable().length === 0)) {
        return;
      }
      this._collectionResync(true);
      if (!options.silent) {
        return this.trigger('resort', this.vm_observable_array());
      }
    }, this);
    if (options.defer) {
      _.defer(_resync);
    } else {
      _resync();
    }
    return this;
  };
  CollectionObservable.prototype.sortAttribute = function(sort_attribute, sorted_index, silent) {
    return this.sortedIndex(sorted_index, sort_attribute, silent);
  };
  CollectionObservable.prototype._sortAttributeFn = function(sort_attribute) {
    return function(models, model) {
      return _.sortedIndex(models, model, function(test) {
        return test.get(sort_attribute);
      });
    };
  };
  CollectionObservable.prototype.viewModelByModel = function(model) {
    var id_attribute;
    if (!this.vm_observable_array) {
      throw new Error("CollectionObservable: cannot get a view model if vm_observable_array was not supplied");
    }
    id_attribute = model.hasOwnProperty(model.idAttribute) ? model.idAttribute : 'cid';
    return _.find(this.vm_observable_array(), function(test) {
      return test.__kb_model[id_attribute] === model[id_attribute];
    });
  };
  CollectionObservable.prototype.eachViewModel = function(iterator) {
    var view_model, _i, _len, _ref, _results;
    _ref = this.vm_observable_array();
    _results = [];
    for (_i = 0, _len = _ref.length; _i < _len; _i++) {
      view_model = _ref[_i];
      _results.push(iterator(view_model));
    }
    return _results;
  };
  CollectionObservable.prototype._onGetValue = function() {
    return this._kb_value_observable();
  };
  CollectionObservable.prototype._onCollectionReset = function() {
    return this._collectionResync();
  };
  CollectionObservable.prototype._onCollectionResort = function(model_or_models) {
    if (this.options.sorted_index) {
      throw new Error("CollectionObservable: collection sorted_index unexpected");
    }
    if (_.isArray(model_or_models)) {
      this._collectionResync(true);
      return this.trigger('resort', this.vm_observable_array());
    } else {
      return this._onModelResort(model_or_models);
    }
  };
  CollectionObservable.prototype._onModelAdd = function(model) {
    var add_index, sorted_models, view_model;
    if (this.options.sorted_index) {
      sorted_models = _.pluck(this.vm_observable_array(), '__kb_model');
      add_index = this.options.sorted_index(sorted_models, model);
    } else {
      add_index = this._kb_collection.indexOf(model);
    }
    if (this.vm_observable_array) {
      view_model = this._viewModelCreate(model);
      this.vm_observable_array.splice(add_index, 0, view_model);
    }
    this._kb_value_observable.splice(add_index, 0, model);
    if (this.vm_observable_array) {
      return this.trigger('add', view_model, this.vm_observable_array());
    }
  };
  CollectionObservable.prototype._onModelRemove = function(model) {
    var view_model;
    this._kb_value_observable.remove(model);
    if (this.vm_observable_array) {
      view_model = this.viewModelByModel(model);
      if (!view_model) {
        return;
      }
      this.vm_observable_array.remove(view_model);
      this.trigger('remove', view_model, this.vm_observable_array());
      kb.vmRelease(view_model);
      return view_model.__kb_model = null;
    }
  };
  CollectionObservable.prototype._onModelChanged = function(model) {
    if (this.options.sorted_index && (!this.options.sort_attribute || model.hasChanged(this.options.sort_attribute))) {
      this._onModelResort(model);
    }
    return this._kb_value_observable.valueHasMutated();
  };
  CollectionObservable.prototype._onModelResort = function(model) {
    var new_index, previous_index, sorted_models, view_model;
    previous_index = this._kb_value_observable.indexOf(model);
    if (this.options.sorted_index) {
      sorted_models = _.clone(this._kb_value_observable());
      sorted_models.splice(previous_index, 1);
      new_index = this.options.sorted_index(sorted_models, model);
    } else {
      new_index = this._kb_collection.indexOf(model);
    }
    if (previous_index === new_index) {
      return;
    }
    if (this.vm_observable_array) {
      view_model = this.viewModelByModel(model);
      this.vm_observable_array.splice(previous_index, 1);
      this.vm_observable_array.splice(new_index, 0, view_model);
    }
    this._kb_value_observable.splice(previous_index, 1);
    this._kb_value_observable.splice(new_index, 0, model);
    if (this.vm_observable_array) {
      return this.trigger('resort', view_model, this.vm_observable_array(), new_index);
    }
  };
  CollectionObservable.prototype._clearViewModels = function(silent) {
    var view_model, view_models, _i, _len, _results;
    if (this.vm_observable_array) {
      if (!silent) {
        this.trigger('remove', this.vm_observable_array());
      }
      view_models = this.vm_observable_array.removeAll();
      _results = [];
      for (_i = 0, _len = view_models.length; _i < _len; _i++) {
        view_model = view_models[_i];
        _results.push(kb.vmRelease(view_model));
      }
      return _results;
    }
  };
  CollectionObservable.prototype._collectionResync = function(silent) {
    var add_index, model, models, view_models, _i, _j, _len, _len2, _ref;
    this._clearViewModels(silent);
    this._kb_value_observable.removeAll();
    if (this.options.sorted_index) {
      models = [];
      _ref = this._kb_collection.models;
      for (_i = 0, _len = _ref.length; _i < _len; _i++) {
        model = _ref[_i];
        add_index = this.options.sorted_index(models, model);
        models.splice(add_index, 0, model);
      }
    } else {
      models = _.clone(this._kb_collection.models);
    }
    if (this.vm_observable_array) {
      view_models = [];
      for (_j = 0, _len2 = models.length; _j < _len2; _j++) {
        model = models[_j];
        view_models.push(this._viewModelCreate(model));
      }
      this.vm_observable_array(view_models);
    }
    this._kb_value_observable(models);
    if (this.vm_observable_array) {
      if (!silent) {
        return this.trigger('add', this.vm_observable_array());
      }
    }
  };
  CollectionObservable.prototype._viewModelCreate = function(model) {
    var view_model;
    if (this.options.view_model_create) {
      view_model = this.options.view_model_create(model);
    } else if (this.options.view_model_constructor) {
      view_model = new this.options.view_model_constructor(model);
    } else {
      view_model = kb.viewModel(model);
    }
    view_model.__kb_model = model;
    return view_model;
  };
  return CollectionObservable;
})();
__extends(Knockback.CollectionObservable.prototype, Backbone.Events);
Knockback.collectionObservable = function(collection, vm_observable_array, options) {
  return new Knockback.CollectionObservable(collection, vm_observable_array, options);
};
Knockback.viewModelGetModel = Knockback.vmModel = function(view_model) {
  return view_model.__kb_model;
};
Knockback.sortedIndexWrapAttr = Knockback.siwa = function(attribute_name, wrapper_constructor) {
  return function(models, model) {
    return _.sortedIndex(models, model, function(test) {
      return new wrapper_constructor(test.get(attribute_name));
    });
  };
};
/*
  knockback_default_wrapper.js
  (c) 2011 Kevin Malakoff.
  Knockback.DefaultWrapper is freely distributable under the MIT license.
  See the following for full license details:
    https://github.com/kmalakoff/knockback/blob/master/LICENSE
*/
var __bind = function(fn, me){ return function(){ return fn.apply(me, arguments); }; };
if (!this.Knockback) {
  throw new Error('Knockback: Dependency alert! knockback_core.js must be included before this file');
}
Knockback.DefaultWrapper = (function() {
  function DefaultWrapper(observable, default_value) {
    this.default_value = default_value;
    _.bindAll(this, 'destroy', 'setToDefault');
    this._kb_observable = ko.dependentObservable({
      read: __bind(function() {
        var value;
        value = ko.utils.unwrapObservable(observable());
        if (!value) {
          return ko.utils.unwrapObservable(this.default_value);
        } else {
          return value;
        }
      }, this),
      write: function(value) {
        return observable(value);
      },
      owner: {}
    });
    this._kb_observable.destroy = this.destroy;
    this._kb_observable.setToDefault = this.setToDefault;
    return kb.wrappedObservable(this);
  }
  DefaultWrapper.prototype.destroy = function() {
    this._kb_observable = null;
    return this.default_value = null;
  };
  DefaultWrapper.prototype.setToDefault = function() {
    return this._kb_observable(this.default_value);
  };
  return DefaultWrapper;
})();
Knockback.defaultWrapper = function(observable, default_value) {
  return new Knockback.DefaultWrapper(observable, default_value);
};
/*
  knockback_formatted_observable.js
  (c) 2011 Kevin Malakoff.
  Knockback.FormattedObservable is freely distributable under the MIT license.
  See the following for full license details:
    https://github.com/kmalakoff/knockback/blob/master/LICENSE
*/if (!this.Knockback) {
  throw new Error('Knockback: Dependency alert! knockback_core.js must be included before this file');
}
Knockback.toFormattedString = function(format) {
  var arg, args, index, parameter_index, result, value;
  result = format.slice();
  args = Array.prototype.slice.call(arguments, 1);
  for (index in args) {
    arg = args[index];
    value = ko.utils.unwrapObservable(arg);
    if (!value) {
      value = '';
    }
    parameter_index = format.indexOf("\{" + index + "\}");
    while (parameter_index >= 0) {
      result = result.replace("{" + index + "}", value);
      parameter_index = format.indexOf("\{" + index + "\}", parameter_index + 1);
    }
  }
  return result;
};
Knockback.parseFormattedString = function(string, format) {
  var count, format_indices_to_matched_indices, index, match_index, matches, parameter_count, parameter_index, positions, regex, regex_string, results, sorted_positions, _i, _results;
  regex_string = format.slice();
  index = 0;
  parameter_count = 0;
  positions = {};
  while (regex_string.search("\\{" + index + "\\}") >= 0) {
    parameter_index = format.indexOf("\{" + index + "\}");
    while (parameter_index >= 0) {
      regex_string = regex_string.replace("\{" + index + "\}", '(.*)');
      positions[parameter_index] = index;
      parameter_count++;
      parameter_index = format.indexOf("\{" + index + "\}", parameter_index + 1);
    }
    index++;
  }
  count = index;
  regex = new RegExp(regex_string);
  matches = regex.exec(string);
  if (matches) {
    matches.shift();
  }
  if (!matches || (matches.length !== parameter_count)) {
    return _.map((function() {
      _results = [];
      for (var _i = 1; 1 <= count ? _i <= count : _i >= count; 1 <= count ? _i++ : _i--){ _results.push(_i); }
      return _results;
    }).apply(this), function() {
      return '';
    });
  }
  sorted_positions = _.sortBy(_.keys(positions), function(parameter_index, format_index) {
    return parseInt(parameter_index, 10);
  });
  format_indices_to_matched_indices = {};
  for (match_index in sorted_positions) {
    parameter_index = sorted_positions[match_index];
    index = positions[parameter_index];
    if (format_indices_to_matched_indices.hasOwnProperty(index)) {
      continue;
    }
    format_indices_to_matched_indices[index] = match_index;
  }
  results = [];
  index = 0;
  while (index < count) {
    results.push(matches[format_indices_to_matched_indices[index]]);
    index++;
  }
  return results;
};
Knockback.formattedObservable = function(format, args) {
  var observable_args, result;
  observable_args = Array.prototype.slice.call(arguments, 1);
  result = ko.dependentObservable({
    read: function() {
      var arg, _i, _len;
      args = [ko.utils.unwrapObservable(format)];
      for (_i = 0, _len = observable_args.length; _i < _len; _i++) {
        arg = observable_args[_i];
        args.push(ko.utils.unwrapObservable(arg));
      }
      return kb.toFormattedString.apply(null, args);
    },
    write: function(value) {
      var index, matches, max_count, _results;
      matches = kb.parseFormattedString(value, ko.utils.unwrapObservable(format));
      max_count = Math.min(observable_args.length, matches.length);
      index = 0;
      _results = [];
      while (index < max_count) {
        observable_args[index](matches[index]);
        _results.push(index++);
      }
      return _results;
    },
    owner: {}
  });
  return result;
};
/*
  knockback_localized_observable.js
  (c) 2011 Kevin Malakoff.
  Knockback.LocalizedObservable is freely distributable under the MIT license.
  See the following for full license details:
    https://github.com/kmalakoff/knockback/blob/master/LICENSE
*/if (!this.Knockback) {
  throw new Error('Knockback: Dependency alert! knockback_core.js must be included before this file');
}
Knockback.LocalizedObservable = (function() {
  function LocalizedObservable(value, options, view_model) {
    this.value = value;
    this.options = options != null ? options : {};
    this.view_model = view_model;
    if (!(this.options.read || this.read)) {
      throw new Error('LocalizedObservable: options.read is missing');
    }
    if (this.options.read && this.read) {
      throw new Error('LocalizedObservable: options.read and read class function exist. You need to choose one.');
    }
    if (this.options.write && this.write) {
      throw new Error('LocalizedObservable: options.write and write class function exist. You need to choose one.');
    }
    if (!kb.locale_manager) {
      throw new Error('LocalizedObservable: Knockback.locale_manager is not defined');
    }
    _.bindAll(this, 'destroy', 'setToDefault', 'resetToCurrent', 'observedValue', '_onGetValue', '_onSetValue', '_onLocaleChange');
    this._kb_read = this.options.read ? this.options.read : this.read;
    this._kb_write = this.options.write ? this.options.write : this.write;
    this._kb_default = this.options["default"] ? this.options["default"] : this["default"];
    if (this.value) {
      value = ko.utils.unwrapObservable(this.value);
    }
    this._kb_value_observable = ko.observable(!value ? this._getDefaultValue() : this._kb_read.call(this, value, null));
    if (this._kb_write) {
      if (!this.view_model) {
        this.view_model = {};
      }
      if (!_.isFunction(this._kb_write)) {
        throw new Error('LocalizedObservable: options.write is not a function for read_write model attribute');
      }
      this._kb_observable = ko.dependentObservable({
        read: this._onGetValue,
        write: this._onSetValue,
        owner: this.view_model
      });
    } else {
      this._kb_observable = ko.dependentObservable(this._onGetValue);
    }
    this._kb_observable.destroy = this.destroy;
    this._kb_observable.observedValue = this.observedValue;
    this._kb_observable.setToDefault = this.setToDefault;
    this._kb_observable.resetToCurrent = this.resetToCurrent;
    kb.locale_manager.bind('change', this._onLocaleChange);
    return kb.wrappedObservable(this);
  }
  LocalizedObservable.prototype.destroy = function() {
    kb.locale_manager.unbind('change', this._onLocaleChange);
    this._kb_value_observable = null;
    this._kb_observable.dispose();
    this._kb_observable = null;
    this.options = {};
    return this.view_model = null;
  };
  LocalizedObservable.prototype.setToDefault = function() {
    var current_value, default_value;
    if (!this._kb_default) {
      return;
    }
    default_value = this._getDefaultValue();
    current_value = this._kb_value_observable();
    if (current_value !== default_value) {
      return this._onSetValue(default_value);
    } else {
      return this._kb_value_observable.valueHasMutated();
    }
  };
  LocalizedObservable.prototype.resetToCurrent = function() {
    this._kb_value_observable(null);
    return this._onSetValue(this._getCurrentValue());
  };
  LocalizedObservable.prototype.observedValue = function(value) {
    if (arguments.length === 0) {
      return this.value;
    }
    this.value = value;
    this._onLocaleChange();
    return this;
  };
  LocalizedObservable.prototype._getDefaultValue = function() {
    if (!this._kb_default) {
      return '';
    }
    if (_.isFunction(this._kb_default)) {
      return this._kb_default();
    } else {
      return this._kb_default;
    }
  };
  LocalizedObservable.prototype._getCurrentValue = function() {
    if (!(this.value && this._kb_observable)) {
      return this._getDefaultValue();
    }
    return this._kb_read.call(this, ko.utils.unwrapObservable(this.value), this._kb_observable);
  };
  LocalizedObservable.prototype._onGetValue = function() {
    if (this.value) {
      ko.utils.unwrapObservable(this.value);
    }
    return this._kb_value_observable();
  };
  LocalizedObservable.prototype._onSetValue = function(value) {
    this._kb_write.call(this, value, ko.utils.unwrapObservable(this.value), this._kb_observable);
    value = this._kb_read.call(this, ko.utils.unwrapObservable(this.value), this._kb_observable);
    this._kb_value_observable(value);
    if (this.options.onChange) {
      return this.options.onChange(value);
    }
  };
  LocalizedObservable.prototype._onLocaleChange = function() {
    var value;
    value = this._kb_read.call(this, ko.utils.unwrapObservable(this.value), this._kb_observable);
    this._kb_value_observable(value);
    if (this.options.onChange) {
      return this.options.onChange(value);
    }
  };
  return LocalizedObservable;
})();
Knockback.localizedObservable = function(value, options, view_model) {
  return new Knockback.LocalizedObservable(value, options, view_model);
};
/*
  knockback_observable.js
  (c) 2011 Kevin Malakoff.
  Knockback.Observable is freely distributable under the MIT license.
  See the following for full license details:
    https://github.com/kmalakoff/knockback/blob/master/LICENSE
*/if (!this.Knockback) {
  throw new Error('Knockback: Dependency alert! knockback_core.js must be included before this file');
}
Knockback.Observable = (function() {
  function Observable(model, options, view_model) {
    this.model = model;
    this.options = options;
    this.view_model = view_model;
    if (!this.model) {
      throw new Error('Observable: model is missing');
    }
    if (!this.options) {
      throw new Error('Observable: options is missing');
    }
    if (_.isString(this.options) || ko.isObservable(this.options)) {
      this.options = {
        key: this.options
      };
    }
    if (!this.options.key) {
      throw new Error('Observable: options.key is missing');
    }
    _.bindAll(this, 'destroy', 'setToDefault', '_onGetValue', '_onSetValue', '_onModelChange', '_onModelLoaded', '_onModelUnloaded');
    if (Backbone.ModelRef && (this.model instanceof Backbone.ModelRef)) {
      this.model_ref = this.model;
      this.model_ref.retain();
      this.model_ref.bind('loaded', this._onModelLoaded);
      this.model_ref.bind('unloaded', this._onModelUnloaded);
      this.model = this.model_ref.getModel();
    }
    this._kb_value_observable = ko.observable();
    if (this.options.localizer) {
      this._kb_localizer = new this.options.localizer(this._getCurrentValue());
    }
    if (this.options.write) {
      if (!this.view_model) {
        this.view_model = {};
      }
      this._kb_observable = ko.dependentObservable({
        read: this._onGetValue,
        write: this._onSetValue,
        owner: this.view_model
      });
    } else {
      this._kb_observable = ko.dependentObservable(this._onGetValue);
    }
    this._kb_observable.destroy = this.destroy;
    this._kb_observable.setToDefault = this.setToDefault;
    if (!this.model_ref || this.model_ref.isLoaded()) {
      this.model.bind('change', this._onModelChange);
    }
    return kb.wrappedObservable(this);
  }
  Observable.prototype.destroy = function() {
    this._kb_value_observable = null;
    this._kb_observable.dispose();
    this._kb_observable = null;
    if (this.model) {
      this._onModelUnloaded(this.model);
    }
    if (this.model_ref) {
      this.model_ref.unbind('loaded', this._onModelLoaded);
      this.model_ref.unbind('unloaded', this._onModelUnloaded);
      this.model_ref.release();
      this.model_ref = null;
    }
    this.options = null;
    return this.view_model = null;
  };
  Observable.prototype.setToDefault = function() {
    var value;
    value = this._getDefaultValue();
    if (this._kb_localizer) {
      this._kb_localizer.observedValue(value);
      value = this._kb_localizer();
    }
    return this._kb_value_observable(value);
  };
  Observable.prototype._getDefaultValue = function() {
    if (!this.options.hasOwnProperty('default')) {
      return '';
    }
    if (_.isFunction(this.options["default"])) {
      return this.options["default"]();
    } else {
      return this.options["default"];
    }
  };
  Observable.prototype._getCurrentValue = function() {
    var arg, args, key, _i, _len, _ref;
    if (!this.model) {
      return this._getDefaultValue();
    }
    key = ko.utils.unwrapObservable(this.options.key);
    args = [key];
    if (!_.isUndefined(this.options.args)) {
      if (_.isArray(this.options.args)) {
        _ref = this.options.args;
        for (_i = 0, _len = _ref.length; _i < _len; _i++) {
          arg = _ref[_i];
          args.push(ko.utils.unwrapObservable(arg));
        }
      } else {
        args.push(ko.utils.unwrapObservable(this.options.args));
      }
    }
    if (this.options.read) {
      return this.options.read.apply(this.view_model, args);
    } else {
      return this.model.get.apply(this.model, args);
    }
  };
  Observable.prototype._onGetValue = function() {
    var arg, value, _i, _len, _ref;
    this._kb_value_observable();
    ko.utils.unwrapObservable(this.options.key);
    if (!_.isUndefined(this.options.args)) {
      if (_.isArray(this.options.args)) {
        _ref = this.options.args;
        for (_i = 0, _len = _ref.length; _i < _len; _i++) {
          arg = _ref[_i];
          ko.utils.unwrapObservable(arg);
        }
      } else {
        ko.utils.unwrapObservable(this.options.args);
      }
    }
    value = this._getCurrentValue();
    if (this._kb_localizer) {
      this._kb_localizer.observedValue(value);
      value = this._kb_localizer();
    }
    return value;
  };
  Observable.prototype._onSetValue = function(value) {
    var arg, args, set_info, _i, _len, _ref;
    if (this._kb_localizer) {
      this._kb_localizer(value);
      value = this._kb_localizer.observedValue();
    }
    if (this.model) {
      set_info = {};
      set_info[ko.utils.unwrapObservable(this.options.key)] = value;
      args = _.isFunction(this.options.write) ? [value] : [set_info];
      if (!_.isUndefined(this.options.args)) {
        if (_.isArray(this.options.args)) {
          _ref = this.options.args;
          for (_i = 0, _len = _ref.length; _i < _len; _i++) {
            arg = _ref[_i];
            args.push(ko.utils.unwrapObservable(arg));
          }
        } else {
          args.push(ko.utils.unwrapObservable(this.options.args));
        }
      }
      if (_.isFunction(this.options.write)) {
        this.options.write.apply(this.view_model, args);
      } else {
        this.model.set.apply(this.model, args);
      }
    }
    if (this._kb_localizer) {
      return this._kb_value_observable(this._kb_localizer());
    } else {
      return this._kb_value_observable(value);
    }
  };
  Observable.prototype._onModelLoaded = function(model) {
    this.model = model;
    this.model.bind('change', this._onModelChange);
    return this._updateValue();
  };
  Observable.prototype._onModelUnloaded = function(model) {
    if (this._kb_localizer && this._kb_localizer.destroy) {
      this._kb_localizer.destroy();
      this._kb_localizer = null;
    }
    this.model.unbind('change', this._onModelChange);
    return this.model = null;
  };
  Observable.prototype._onModelChange = function() {
    if ((this.model && this.model.hasChanged) && !this.model.hasChanged(ko.utils.unwrapObservable(this.options.key))) {
      return;
    }
    return this._updateValue();
  };
  Observable.prototype._updateValue = function() {
    var value;
    value = this._getCurrentValue();
    if (this._kb_localizer) {
      this._kb_localizer.observedValue(value);
      value = this._kb_localizer();
    }
    return this._kb_value_observable(value);
  };
  return Observable;
})();
Knockback.observable = function(model, options, view_model) {
  return new Knockback.Observable(model, options, view_model);
};
/*
  knockback_observables.js
  (c) 2011 Kevin Malakoff.
  Knockback.Observables is freely distributable under the MIT license.
  See the following for full license details:
    https://github.com/kmalakoff/knockback/blob/master/LICENSE
*/if (!this.Knockback) {
  throw new Error('Knockback: Dependency alert! knockback_core.js must be included before this file');
}
Knockback.Observables = (function() {
  function Observables(model, mappings_info, view_model, options_or_writeable) {
    var is_string, mapping_info, view_model_property_name, write, _ref, _ref2;
    this.model = model;
    this.mappings_info = mappings_info;
    this.view_model = view_model;
    if (!this.model) {
      throw new Error('Observables: model is missing');
    }
    if (!this.mappings_info) {
      throw new Error('Observables: mappings_info is missing');
    }
    if (!!options_or_writeable && ((_.isBoolean(options_or_writeable) && options_or_writeable) || !!options_or_writeable.write)) {
      write = _.isBoolean(options_or_writeable) ? options_or_writeable : !!options_or_writeable.write;
      _ref = this.mappings_info;
      for (view_model_property_name in _ref) {
        mapping_info = _ref[view_model_property_name];
        is_string = _.isString(mapping_info);
        if (is_string || !mapping_info.hasOwnProperty(write)) {
          mapping_info = is_string ? {
            key: mapping_info,
            write: write
          } : _.extend({
            write: write
          }, mapping_info);
        }
        this.view_model[view_model_property_name] = kb.observable(this.model, mapping_info, this.view_model);
      }
    } else {
      _ref2 = this.mappings_info;
      for (view_model_property_name in _ref2) {
        mapping_info = _ref2[view_model_property_name];
        this.view_model[view_model_property_name] = kb.observable(this.model, mapping_info, this.view_model);
      }
    }
  }
  Observables.prototype.destroy = function() {
    var mapping_info, view_model_property_name, _ref;
    _ref = this.mappings_info;
    for (view_model_property_name in _ref) {
      mapping_info = _ref[view_model_property_name];
      if (this.view_model[view_model_property_name]) {
        this.view_model[view_model_property_name].destroy();
      }
      this.view_model[view_model_property_name] = null;
    }
    this.view_model = null;
    this.mappings_info = null;
    return this.model = null;
  };
  Observables.prototype.setToDefault = function() {
    var mapping_info, view_model_property_name, _ref, _results;
    _ref = this.mappings_info;
    _results = [];
    for (view_model_property_name in _ref) {
      mapping_info = _ref[view_model_property_name];
      _results.push(this.view_model[view_model_property_name].setToDefault());
    }
    return _results;
  };
  return Observables;
})();
Knockback.observables = function(model, mappings_info, view_model, options) {
  return new Knockback.Observables(model, mappings_info, view_model, options);
};
/*
  knockback_triggered_observable.js
  (c) 2011 Kevin Malakoff.
  Knockback.Observable is freely distributable under the MIT license.
  See the following for full license details:
    https://github.com/kmalakoff/knockback/blob/master/LICENSE
*/if (!this.Knockback) {
  throw new Error('Knockback: Dependency alert! knockback_core.js must be included before this file');
}
Knockback.TriggeredObservable = (function() {
  function TriggeredObservable(model, event_name) {
    this.model = model;
    this.event_name = event_name;
    if (!this.model) {
      throw new Error('Observable: model is missing');
    }
    if (!this.event_name) {
      throw new Error('Observable: event_name is missing');
    }
    _.bindAll(this, 'destroy', '_onGetValue', '_onValueChange', '_onModelLoaded', '_onModelUnloaded');
    if (Backbone.ModelRef && (this.model instanceof Backbone.ModelRef)) {
      this.model_ref = this.model;
      this.model_ref.retain();
      this.model_ref.bind('loaded', this._onModelLoaded);
      this.model_ref.bind('unloaded', this._onModelUnloaded);
      this.model = this.model_ref.getModel();
    }
    this._kb_value_observable = ko.observable();
    this._kb_observable = ko.dependentObservable(this._onGetValue);
    this._kb_observable.destroy = this.destroy;
    if (!this.model_ref || this.model_ref.isLoaded()) {
      this._onModelLoaded(this.model);
    }
    return kb.wrappedObservable(this);
  }
  TriggeredObservable.prototype.destroy = function() {
    this._kb_observable.dispose();
    this._kb_observable = null;
    this._kb_value_observable = null;
    if (this.model) {
      this._onModelUnloaded(this.model);
    }
    if (this.model_ref) {
      this.model_ref.unbind('loaded', this._onModelLoaded);
      this.model_ref.unbind('unloaded', this._onModelUnloaded);
      this.model_ref.release();
      this.model_ref = null;
    }
    this.options = null;
    return this.view_model = null;
  };
  TriggeredObservable.prototype._onGetValue = function() {
    return this._kb_value_observable();
  };
  TriggeredObservable.prototype._onModelLoaded = function(model) {
    this.model = model;
    this.model.bind(this.event_name, this._onValueChange);
    return this._onValueChange();
  };
  TriggeredObservable.prototype._onModelUnloaded = function() {
    if (this._kb_localizer && this._kb_localizer.destroy) {
      this._kb_localizer.destroy();
      this._kb_localizer = null;
    }
    this.model.unbind(this.event_name, this._onValueChange);
    return this.model = null;
  };
  TriggeredObservable.prototype._onValueChange = function() {
    var current_value;
    current_value = this._kb_value_observable();
    if (current_value !== this.model) {
      return this._kb_value_observable(this.model);
    } else {
      return this._kb_value_observable.valueHasMutated();
    }
  };
  return TriggeredObservable;
})();
Knockback.triggeredObservable = function(model, event_name) {
  return new Knockback.TriggeredObservable(model, event_name);
};
/*
  knockback_view_model.js
  (c) 2011 Kevin Malakoff.
  Knockback.Observable is freely distributable under the MIT license.
  See the following for full license details:
    https://github.com/kmalakoff/knockback/blob/master/LICENSE
*/
var AttributeConnector;
var __bind = function(fn, me){ return function(){ return fn.apply(me, arguments); }; }, __hasProp = Object.prototype.hasOwnProperty, __extends = function(child, parent) {
  for (var key in parent) { if (__hasProp.call(parent, key)) child[key] = parent[key]; }
  function ctor() { this.constructor = child; }
  ctor.prototype = parent.prototype;
  child.prototype = new ctor;
  child.__super__ = parent.prototype;
  return child;
};
if (!this.Knockback) {
  throw new Error('Knockback: Dependency alert! knockback_core.js must be included before this file');
}
AttributeConnector = (function() {
  function AttributeConnector(model, key, read_only) {
    this.key = key;
    this.read_only = read_only;
    _.bindAll(this, 'destroy', 'setModel');
    this._kb_observable = ko.observable();
    this._kb_observable.subscription = this._kb_observable.subscribe(__bind(function(value) {
      var set_info;
      if (this.read_only) {
        if (this.model) {
          value = this.model.get(this.key);
          if (this._kb_observable() === value) {
            return;
          }
          this._kb_observable(value);
        }
        throw "Cannot write a value to a dependentObservable unless you specify a 'write' option. If you wish to read the current value, don't pass any parameters.";
      } else if (this.model) {
        set_info = {};
        set_info[this.key] = value;
        return this.model.set(set_info);
      }
    }, this));
    this._kb_observable.destroy = this.destroy;
    this._kb_observable.setModel = this.setModel;
    if (model) {
      this.setModel(model);
    }
    return kb.wrappedObservable(this);
  }
  AttributeConnector.prototype.destroy = function() {
    this.model = null;
    return this._kb_observable = null;
  };
  AttributeConnector.prototype.setModel = function(model) {
    if (model) {
      this.model = model;
      return this._kb_observable(this.model.get(this.key));
    } else {
      return this.model = null;
    }
  };
  return AttributeConnector;
})();
Knockback.ViewModel_RCBase = (function() {
  function ViewModel_RCBase() {
    this._kb_vm = {};
    this._kb_vm.ref_count = 1;
  }
  ViewModel_RCBase.extend = Backbone.Model.extend;
  ViewModel_RCBase.prototype.__destroy = function() {
    return kb.vmReleaseObservables(this);
  };
  ViewModel_RCBase.prototype.retain = function() {
    if (this._kb_vm.ref_count <= 0) {
      throw new Error("ViewModel: ref_count is corrupt: " + this._kb_vm.ref_count);
    }
    this._kb_vm.ref_count++;
    return this;
  };
  ViewModel_RCBase.prototype.release = function() {
    if (this._kb_vm.ref_count <= 0) {
      throw new Error("ViewModel: ref_count is corrupt: " + this._kb_vm.ref_count);
    }
    this._kb_vm.ref_count--;
    if (!this._kb_vm.ref_count) {
      this.__destroy();
    }
    return this;
  };
  ViewModel_RCBase.prototype.refCount = function() {
    return this._kb_vm.ref_count;
  };
  return ViewModel_RCBase;
})();
Knockback.ViewModel = (function() {
  __extends(ViewModel, kb.ViewModel_RCBase);
  function ViewModel(model, options, view_model) {
    var key, missing, _i, _len;
    if (options == null) {
      options = {};
    }
    ViewModel.__super__.constructor.apply(this, arguments);
    this._kb_vm.model = model;
    this._kb_vm.options = options;
    this._kb_vm.view_model = view_model;
    if (!this._kb_vm.model) {
      throw new Error('ViewModel: model is missing');
    }
    _.bindAll(this, '_kb_vm_onModelChange', '_kb_vm_onModelLoaded', '_kb_vm_onModelUnloaded');
    if (!this._kb_vm.view_model) {
      this._kb_vm.view_model = this;
    } else {
      this._kb_vm.observables = [];
    }
    if (Backbone.ModelRef && (this._kb_vm.model instanceof Backbone.ModelRef)) {
      this._kb_vm.model_ref = this._kb_vm.model;
      this._kb_vm.model_ref.retain();
      this._kb_vm.model_ref.bind('loaded', this._kb_vm_onModelLoaded);
      this._kb_vm.model_ref.bind('unloaded', this._kb_vm_onModelUnloaded);
      this._kb_vm.model = this._kb_vm.model_ref.getModel();
    }
    if (!this._kb_vm.model_ref || this._kb_vm.model_ref.isLoaded()) {
      this._kb_vm_onModelLoaded(this._kb_vm.model);
    }
    if (!this._kb_vm.options.internals && !this._kb_vm.options.requires) {
      return this;
    }
    missing = _.union((this._kb_vm.options.internals ? this._kb_vm.options.internals : []), (this._kb_vm.options.requires ? this._kb_vm.options.requires : []));
    if (!this._kb_vm.model_ref || this._kb_vm.model_ref.isLoaded()) {
      missing = _.difference(missing, _.keys(this._kb_vm.model.attributes));
    }
    for (_i = 0, _len = missing.length; _i < _len; _i++) {
      key = missing[_i];
      this._updateAttributeObservor(this._kb_vm.model, key);
    }
  }
  ViewModel.prototype.__destroy = function() {
    var view_model;
    if (this._kb_vm.model) {
      this._kb_vm.model.unbind('change', this._kb_vm_onModelChange);
      this._kb_vm.model = null;
    }
    view_model = this._kb_vm.view_model;
    this._kb_vm.view_model = null;
    kb.vmReleaseObservables(view_model, this._kb_vm.observables);
    if (this._kb_vm.observables) {
      return this._kb_vm.observables = null;
    }
  };
  ViewModel.prototype._kb_vm_onModelLoaded = function(model) {
    var key, _results;
    this._kb_vm.model = model;
    this._kb_vm.model.bind('change', this._kb_vm_onModelChange);
    _results = [];
    for (key in this._kb_vm.model.attributes) {
      _results.push(this._updateAttributeObservor(this._kb_vm.model, key));
    }
    return _results;
  };
  ViewModel.prototype._kb_vm_onModelUnloaded = function(model) {
    var key, _results;
    this._kb_vm.model.unbind('change', this._kb_vm_onModelChange);
    model = this._kb_vm.model;
    this._kb_vm.model = null;
    _results = [];
    for (key in model.attributes) {
      _results.push(this._updateAttributeObservor(this._kb_vm.model, key));
    }
    return _results;
  };
  ViewModel.prototype._kb_vm_onModelChange = function() {
    var key, _results, _results2;
    if (this._kb_vm.model._changed) {
      _results = [];
      for (key in this._kb_vm.model.attributes) {
        _results.push((this._kb_vm.model.hasChanged(key) ? this._updateAttributeObservor(this._kb_vm.model, key) : void 0));
      }
      return _results;
    } else if (this._kb_vm.model.changed) {
      _results2 = [];
      for (key in this._kb_vm.model.changed) {
        _results2.push(this._updateAttributeObservor(this._kb_vm.model, key));
      }
      return _results2;
    }
  };
  ViewModel.prototype._updateAttributeObservor = function(model, key) {
    var vm_key;
    vm_key = this._kb_vm.options.internals && _.contains(this._kb_vm.options.internals, key) ? '_' + key : key;
    if (this._kb_vm.view_model.hasOwnProperty(vm_key)) {
      if (this._kb_vm.view_model[vm_key]) {
        return this._kb_vm.view_model[vm_key].setModel(model);
      }
    } else {
      if (this._kb_vm.observables) {
        this._kb_vm.observables.push(vm_key);
      }
      return this._kb_vm.view_model[vm_key] = new AttributeConnector(model, key, this._kb_vm.options.read_only);
    }
  };
  return ViewModel;
})();
Knockback.viewModel = function(model, options, view_model) {
  return new Knockback.ViewModel(model, options, view_model);
};