|
|
@@ -7,29 +7,45 @@ var config = require('./config'),
|
|
|
api = {}
|
|
|
|
|
|
/*
|
|
|
- * Allows user to create a custom directive
|
|
|
+ * Set config options
|
|
|
*/
|
|
|
-api.directive = function (name, fn) {
|
|
|
- if (!fn) return directives[name]
|
|
|
- directives[name] = fn
|
|
|
+api.config = function (opts) {
|
|
|
+ if (opts) {
|
|
|
+ utils.extend(config, opts)
|
|
|
+ textParser.buildRegex()
|
|
|
+ }
|
|
|
}
|
|
|
|
|
|
/*
|
|
|
- * Allows user to create a custom filter
|
|
|
+ * Allows user to register/retrieve a directive definition
|
|
|
*/
|
|
|
-api.filter = function (name, fn) {
|
|
|
- if (!fn) return filters[name]
|
|
|
- filters[name] = fn
|
|
|
+api.directive = function (id, fn) {
|
|
|
+ if (!fn) return directives[id]
|
|
|
+ directives[id] = fn
|
|
|
}
|
|
|
|
|
|
/*
|
|
|
- * Set config options
|
|
|
+ * Allows user to register/retrieve a filter function
|
|
|
*/
|
|
|
-api.config = function (opts) {
|
|
|
- if (opts) {
|
|
|
- utils.extend(config, opts)
|
|
|
- textParser.buildRegex()
|
|
|
- }
|
|
|
+api.filter = function (id, fn) {
|
|
|
+ if (!fn) return filters[id]
|
|
|
+ filters[id] = fn
|
|
|
+}
|
|
|
+
|
|
|
+/*
|
|
|
+ * Allows user to register/retrieve a ViewModel constructor
|
|
|
+ */
|
|
|
+api.vm = function (id, Ctor) {
|
|
|
+ if (!Ctor) return utils.vms[id]
|
|
|
+ utils.vms[id] = Ctor
|
|
|
+}
|
|
|
+
|
|
|
+/*
|
|
|
+ * Allows user to register/retrieve a template partial
|
|
|
+ */
|
|
|
+api.partial = function (id, partial) {
|
|
|
+ if (!partial) return utils.partials[id]
|
|
|
+ utils.partials[id] = partial
|
|
|
}
|
|
|
|
|
|
api.ViewModel = ViewModel
|
|
|
@@ -40,33 +56,21 @@ ViewModel.extend = extend
|
|
|
* and add extend method
|
|
|
*/
|
|
|
function extend (options) {
|
|
|
- var ParentVM = this,
|
|
|
- ExtendedVM = function (opts) {
|
|
|
- opts = opts || {}
|
|
|
- // extend instance data
|
|
|
- if (options.data) {
|
|
|
- opts.data = opts.data || {}
|
|
|
- utils.extend(opts.data, options.data)
|
|
|
- }
|
|
|
- // copy in constructor options, but instance options
|
|
|
- // have priority.
|
|
|
- for (var key in options) {
|
|
|
- if (key !== 'props' &&
|
|
|
- key !== 'data' &&
|
|
|
- key !== 'template' &&
|
|
|
- key !== 'el') {
|
|
|
- opts[key] = opts[key] || options[key]
|
|
|
- }
|
|
|
- }
|
|
|
- ParentVM.call(this, opts)
|
|
|
- }
|
|
|
- // inherit from ViewModel
|
|
|
+ var ParentVM = this
|
|
|
+ // inherit options
|
|
|
+ options = inheritOptions(options, ParentVM.options, true)
|
|
|
+ var ExtendedVM = function (opts) {
|
|
|
+ opts = inheritOptions(opts, options, true)
|
|
|
+ ParentVM.call(this, opts)
|
|
|
+ }
|
|
|
+ // inherit prototype props
|
|
|
var proto = ExtendedVM.prototype = Object.create(ParentVM.prototype)
|
|
|
utils.defProtected(proto, 'constructor', ExtendedVM)
|
|
|
// copy prototype props
|
|
|
if (options.props) {
|
|
|
utils.extend(proto, options.props, function (key) {
|
|
|
- return !(key in ParentVM.prototype)
|
|
|
+ // do not overwrite the ancestor ViewModel prototype methods
|
|
|
+ return !(key in ViewModel.prototype)
|
|
|
})
|
|
|
}
|
|
|
// convert template to documentFragment
|
|
|
@@ -80,6 +84,33 @@ function extend (options) {
|
|
|
return ExtendedVM
|
|
|
}
|
|
|
|
|
|
+/*
|
|
|
+ * Inherit options
|
|
|
+ *
|
|
|
+ * For options such as `data`, `vms`, `directives`, 'partials',
|
|
|
+ * they should be further extended. However extending should only
|
|
|
+ * be done at top level.
|
|
|
+ *
|
|
|
+ * `props` is an exception because it's handled directly on the
|
|
|
+ * prototype.
|
|
|
+ *
|
|
|
+ * `el` is an exception because it's not allowed as an
|
|
|
+ * extension option, but only as an instance option.
|
|
|
+ */
|
|
|
+function inheritOptions (child, parent, topLevel) {
|
|
|
+ child = child || {}
|
|
|
+ if (!parent) return child
|
|
|
+ for (var key in parent) {
|
|
|
+ if (key === 'el' || key === 'props') continue
|
|
|
+ if (!child[key]) { // child has priority
|
|
|
+ child[key] = parent[key]
|
|
|
+ } else if (topLevel && utils.typeOf(child[key]) === 'Object') {
|
|
|
+ inheritOptions(child[key], parent[key], false)
|
|
|
+ }
|
|
|
+ }
|
|
|
+ return child
|
|
|
+}
|
|
|
+
|
|
|
/*
|
|
|
* Convert a string template to a dom fragment
|
|
|
*/
|