{"version":3,"file":"ractive.mjs","sources":["../../../src/polyfills/Object.assign.js","../../../src/utils/object.js","../../../src/utils/is.js","../../../src/polyfills/array.find.js","../../../src/polyfills/node.contains.js","../../../src/polyfills/performance.now.js","../../../src/polyfills/Promise.js","../../../src/polyfills/requestAnimationFrame.js","../../../src/Ractive/config/defaults.js","../../../src/Ractive/static/easing.js","../../../src/config/environment.js","../../../src/utils/noop.js","../../../src/utils/log.js","../../../src/config/errors.js","../../../src/shared/registry.js","../../../src/shared/interpolate.js","../../../src/Ractive/static/interpolators.js","../../../src/shared/keypaths.js","../../../src/utils/array.js","../../../src/global/capture.js","../../../src/model/specials/KeyModel.js","../../../src/shared/methodCallers.js","../../../src/model/specials/KeypathModel.js","../../../src/utils/bind.js","../../../src/model/ModelBase.js","../../../src/shared/rebind.js","../../../src/model/LinkModel.js","../../../src/global/TransitionManager.js","../../../src/global/runloop.js","../../../src/shared/Ticker.js","../../../src/model/helpers/getPrefixer.js","../../../src/model/Model.js","../../../src/model/specials/SharedModel.js","../../../src/view/resolvers/resolveReference.js","../../../src/shared/getRactiveContext.js","../../../src/shared/set.js","../../../src/Ractive/prototype/shared/add.js","../../../src/Ractive/prototype/add.js","../../../src/Ractive/prototype/animate.js","../../../src/events/eventStack.js","../../../src/events/fireEvent.js","../../../src/events/Hook.js","../../../src/shared/anchors.js","../../../src/Ractive/prototype/attachChild.js","../../../src/Ractive/prototype/detach.js","../../../src/Ractive/prototype/detachChild.js","../../../src/Ractive/prototype/find.js","../../../src/Ractive/prototype/findAll.js","../../../src/Ractive/prototype/findAllComponents.js","../../../src/Ractive/prototype/findComponent.js","../../../src/Ractive/prototype/findContainer.js","../../../src/Ractive/prototype/findParent.js","../../../src/config/types.js","../../../src/view/items/shared/findElement.js","../../../src/shared/getNewIndices.js","../../../src/Ractive/prototype/shared/makeArrayMethod.js","../../../src/Ractive/prototype/update.js","../../../src/shared/Context.js","../../../src/Ractive/prototype/fire.js","../../../src/Ractive/prototype/get.js","../../../src/Ractive/static/getContext.js","../../../src/Ractive/prototype/getContext.js","../../../src/config/namespaces.js","../../../src/utils/dom.js","../../../src/Ractive/prototype/insert.js","../../../src/Ractive/prototype/link.js","../../../src/Ractive/prototype/observe/Observer.js","../../../src/Ractive/prototype/observe/Pattern.js","../../../src/Ractive/prototype/observe/Array.js","../../../src/Ractive/prototype/observe.js","../../../src/Ractive/prototype/observeOnce.js","../../../src/Ractive/prototype/shared/trim.js","../../../src/Ractive/prototype/shared/notEmptyString.js","../../../src/Ractive/prototype/off.js","../../../src/Ractive/prototype/on.js","../../../src/Ractive/prototype/once.js","../../../src/Ractive/prototype/pop.js","../../../src/Ractive/prototype/push.js","../../../src/Ractive/prototype/readLink.js","../../../src/global/css.js","../../../src/Ractive/config/custom/adapt.js","../../../src/utils/cleanCss.js","../../../src/Ractive/config/custom/css/transform.js","../../../src/utils/id.js","../../../src/Ractive/static/styleSet.js","../../../src/model/specials/CSSModel.js","../../../src/Ractive/config/custom/css/css.js","../../../src/Ractive/config/custom/data.js","../../../src/config/template.js","../../../src/parse/utils/createFunction.js","../../../src/parse/Parser.js","../../../src/parse/converters/mustache/readDelimiterChange.js","../../../src/parse/converters/expressions/primary/literal/readRegexpLiteral.js","../../../src/utils/escapeRegExp.js","../../../src/parse/converters/utils/getLowestIndex.js","../../../src/utils/html.js","../../../src/parse/converters/expressions/shared/errors.js","../../../src/parse/converters/expressions/primary/literal/readNumberLiteral.js","../../../src/parse/converters/expressions/primary/literal/readBooleanLiteral.js","../../../src/parse/converters/expressions/primary/literal/stringLiteral/makeQuotedStringMatcher.js","../../../src/parse/converters/expressions/primary/literal/readStringLiteral.js","../../../src/parse/converters/expressions/primary/literal/readTemplateStringLiteral.js","../../../src/parse/converters/expressions/shared/patterns.js","../../../src/parse/converters/expressions/shared/readKey.js","../../../src/parse/converters/expressions/primary/literal/objectLiteral/keyValuePair.js","../../../src/parse/converters/expressions/primary/literal/objectLiteral/keyValuePairs.js","../../../src/parse/converters/expressions/primary/literal/readObjectLiteral.js","../../../src/parse/converters/expressions/primary/literal/readArrayLiteral.js","../../../src/parse/converters/expressions/primary/readLiteral.js","../../../src/parse/converters/expressions/primary/readReference.js","../../../src/parse/converters/expressions/primary/readBracketedExpression.js","../../../src/parse/converters/expressions/readPrimary.js","../../../src/parse/converters/expressions/shared/readRefinement.js","../../../src/parse/converters/expressions/readMemberOrInvocation.js","../../../src/parse/converters/expressions/readTypeof.js","../../../src/parse/converters/expressions/readLogicalOr.js","../../../src/parse/converters/expressions/readConditional.js","../../../src/parse/converters/readExpression.js","../../../src/parse/converters/expressions/shared/readExpressionList.js","../../../src/parse/converters/readExpressionOrReference.js","../../../src/parse/utils/flattenExpression.js","../../../src/parse/utils/refineExpression.js","../../../src/parse/converters/element/readAttribute.js","../../../src/parse/converters/readMustache.js","../../../src/parse/converters/mustache/readTriple.js","../../../src/parse/converters/mustache/readUnescaped.js","../../../src/parse/converters/mustache/readAliases.js","../../../src/parse/converters/mustache/readPartial.js","../../../src/parse/converters/mustache/readMustacheComment.js","../../../src/parse/converters/mustache/readInterpolator.js","../../../src/parse/converters/mustache/section/readClosing.js","../../../src/parse/converters/mustache/section/readElse.js","../../../src/parse/converters/mustache/section/readElseIf.js","../../../src/parse/converters/mustache/handlebarsBlockCodes.js","../../../src/parse/converters/mustache/readSection.js","../../../src/parse/converters/readHtmlComment.js","../../../src/parse/utils/stripStandalones.js","../../../src/parse/utils/trimWhitespace.js","../../../src/parse/utils/cleanup.js","../../../src/parse/converters/element/readClosingTag.js","../../../src/parse/converters/readElement.js","../../../src/parse/converters/readText.js","../../../src/parse/converters/readPartialDefinitionSection.js","../../../src/parse/converters/readTemplate.js","../../../src/parse/utils/insertExpressions.js","../../../src/Ractive/shared.js","../../../src/parse/_parse.js","../../../src/Ractive/config/runtime-parser.js","../../../src/shared/getFunction.js","../../../src/Ractive/config/custom/template.js","../../../src/Ractive/config/registries.js","../../../src/Ractive/config/wrapPrototypeMethod.js","../../../src/Ractive/config/deprecate.js","../../../src/Ractive/config/config.js","../../../src/view/items/shared/Item.js","../../../src/model/ComputationChild.js","../../../src/model/Computation.js","../../../src/view/resolvers/ExpressionProxy.js","../../../src/view/resolvers/ReferenceExpressionProxy.js","../../../src/view/resolvers/resolve.js","../../../src/view/items/Alias.js","../../../src/utils/hyphenateCamel.js","../../../src/view/helpers/specialAttrs.js","../../../src/view/items/element/attribute/getUpdateDelegate.js","../../../src/view/items/element/attribute/propertyNames.js","../../../src/view/items/element/ConditionalAttribute.js","../../../src/view/items/element/Attribute.js","../../../src/view/items/element/BindingFlag.js","../../../src/view/items/Comment.js","../../../src/Ractive/prototype/teardown.js","../../../src/model/specials/RactiveModel.js","../../../src/model/RootModel.js","../../../src/Ractive/helpers/getComputationSignature.js","../../../src/Ractive/helpers/subscribe.js","../../../src/Ractive/construct.js","../../../src/view/items/Component.js","../../../src/view/items/shared/directiveArgs.js","../../../src/view/items/element/Decorator.js","../../../src/view/items/Doctype.js","../../../src/view/items/element/binding/Binding.js","../../../src/view/items/element/binding/handleDomEvent.js","../../../src/view/items/element/binding/CheckboxBinding.js","../../../src/view/items/element/binding/getBindingGroup.js","../../../src/view/items/element/binding/CheckboxNameBinding.js","../../../src/view/items/element/binding/ContentEditableBinding.js","../../../src/view/items/element/binding/GenericBinding.js","../../../src/view/items/element/binding/FileBinding.js","../../../src/utils/getSelectedOptions.js","../../../src/view/items/element/binding/MultipleSelectBinding.js","../../../src/view/items/element/binding/NumericBinding.js","../../../src/view/items/element/binding/RadioBinding.js","../../../src/view/items/element/binding/RadioNameBinding.js","../../../src/view/items/element/binding/SingleSelectBinding.js","../../../src/view/items/element/binding/selectBinding.js","../../../src/view/items/Element.js","../../../src/view/items/element/specials/Form.js","../../../src/view/items/element/ElementEvents.js","../../../src/view/items/component/RactiveEvent.js","../../../src/view/items/shared/EventDirective.js","../../../src/view/items/shared/progressiveText.js","../../../src/view/items/shared/Mustache.js","../../../src/view/items/Interpolator.js","../../../src/view/items/element/specials/Input.js","../../../src/utils/parseJSON.js","../../../src/view/items/component/Mapping.js","../../../src/view/items/element/specials/Option.js","../../../src/view/items/partial/getPartialTemplate.js","../../../src/view/items/Partial.js","../../../src/view/RepeatedFragment.js","../../../src/view/items/Section.js","../../../src/view/items/element/specials/Select.js","../../../src/view/items/element/specials/Textarea.js","../../../src/view/items/Text.js","../../../src/config/visibility.js","../../../src/view/items/element/transitions/prefix.js","../../../src/view/items/element/transitions/hyphenate.js","../../../src/view/items/element/transitions/createTransitions.js","../../../src/view/items/element/Transition.js","../../../src/view/items/triple/insertHtml.js","../../../src/view/items/Triple.js","../../../src/view/items/component/getComponentConstructor.js","../../../src/view/items/asyncProxy.js","../../../src/view/items/createItem.js","../../../src/view/helpers/processItems.js","../../../src/view/Fragment.js","../../../src/events/HookQueue.js","../../../src/Ractive/initialise.js","../../../src/Ractive/render.js","../../../src/Ractive/prototype/render.js","../../../src/Ractive/prototype/reset.js","../../../src/Ractive/prototype/resetPartial.js","../../../src/Ractive/prototype/resetTemplate.js","../../../src/Ractive/prototype/reverse.js","../../../src/Ractive/prototype/set.js","../../../src/Ractive/prototype/shift.js","../../../src/Ractive/prototype/sort.js","../../../src/Ractive/prototype/splice.js","../../../src/Ractive/prototype/subtract.js","../../../src/Ractive/prototype/toggle.js","../../../src/Ractive/prototype/toCSS.js","../../../src/Ractive/prototype/toHTML.js","../../../src/Ractive/prototype/toText.js","../../../src/Ractive/prototype/transition.js","../../../src/Ractive/prototype/unlink.js","../../../src/Ractive/prototype/unrender.js","../../../src/Ractive/prototype/unshift.js","../../../src/Ractive/prototype/updateModel.js","../../../src/Ractive/prototype.js","../../../src/Ractive/static/isInstance.js","../../../src/Ractive/static/styleGet.js","../../../src/Ractive/static/sharedSet.js","../../../src/Ractive/static/sharedGet.js","../../../src/extend/_extend.js","../../../src/extend/_macro.js","../../../src/Ractive/static/keypaths.js","../../../src/Ractive/static/findPlugin.js","../../../src/Ractive.js"],"sourcesContent":["/* istanbul ignore if */\nif (!Object.assign) {\n\tObject.assign = function (target, ...sources) {\n\t\tif (target == null)\n\t\t\tthrow new TypeError('Cannot convert undefined or null to object');\n\n\t\tconst to = Object(target);\n\t\tconst sourcesLength = sources.length;\n\n\t\tfor (let index = 0; index < sourcesLength; index++) {\n\t\t\tconst nextSource = sources[index];\n\t\t\tfor (const nextKey in nextSource) {\n\t\t\t\tif (!Object.prototype.hasOwnProperty.call(nextSource, nextKey)) continue;\n\t\t\t\tto[nextKey] = nextSource[nextKey];\n\t\t\t}\n\t\t}\n\n\t\treturn to;\n\t};\n}\n","export function hasOwn ( obj, prop ) {\n\treturn Object.prototype.hasOwnProperty.call( obj, prop );\n}\n\nexport function fillGaps ( target, ...sources ) {\n\tfor (let i = 0; i < sources.length; i++){\n\t\tconst source = sources[i];\n\t\tfor ( const key in source ) {\n\t\t\t// Source can be a prototype-less object.\n\t\t\tif ( key in target || !hasOwn( source, key ) ) continue;\n\t\t\ttarget[ key ] = source[ key ];\n\t\t}\n\t}\n\n\treturn target;\n}\n\nexport function toPairs ( obj = {} ) {\n\tconst pairs = [];\n\tfor ( const key in obj ) {\n\t\t// Source can be a prototype-less object.\n\t\tif ( !hasOwn( obj, key ) ) continue;\n\t\tpairs.push( [ key, obj[ key ] ] );\n\t}\n\treturn pairs;\n}\n\nconst obj = Object;\n\nexport const assign = obj.assign;\n\nexport const create = obj.create;\n\nexport const defineProperty = obj.defineProperty;\n\nexport const defineProperties = obj.defineProperties;\n\nexport const keys = obj.keys;\n","const toString = Object.prototype.toString;\nconst arrayLikePattern = /^\\[object (?:Array|FileList)\\]$/;\n\nexport function isArrayLike ( obj ) {\n\treturn arrayLikePattern.test( toString.call( obj ) );\n}\n\nexport const isArray = Array.isArray;\n\nexport function isEqual ( a, b ) {\n\tif ( a === null && b === null ) {\n\t\treturn true;\n\t}\n\n\tif ( isObjectType( a ) || isObjectType( b ) ) {\n\t\treturn false;\n\t}\n\n\treturn a === b;\n}\n\n// http://stackoverflow.com/questions/18082/validate-numbers-in-javascript-isnumeric\nexport function isNumeric ( thing ) {\n\treturn !isNaN( parseFloat( thing ) ) && isFinite( thing );\n}\n\nexport function isObject ( thing ) {\n\treturn ( thing && toString.call( thing ) === '[object Object]' );\n}\n\nexport function isObjectLike ( thing ) {\n\treturn !!( thing && ( isObjectType( thing ) || isFunction( thing ) ) );\n}\n\nexport function isObjectType ( thing ) {\n\treturn typeof thing === 'object';\n}\n\nexport function isFunction ( thing ) {\n\treturn typeof thing === 'function';\n}\n\nexport function isString ( thing ) {\n\treturn typeof thing === 'string';\n}\n\nexport function isNumber ( thing ) {\n\treturn typeof thing === 'number';\n}\n","import { hasOwn, defineProperty } from 'utils/object';\nimport { isFunction } from 'utils/is';\n\n/* istanbul ignore if */\nif (!Array.prototype.find) {\n\tdefineProperty( Array.prototype, 'find', {\n\t\tvalue (callback, thisArg) {\n\t\t\tif (this === null || this === undefined)\n\t\t\t\tthrow new TypeError('Array.prototype.find called on null or undefined');\n\n\t\t\tif (!isFunction( callback ))\n\t\t\t\tthrow new TypeError(`${callback} is not a function`);\n\n\t\t\tconst array = Object(this);\n\t\t\tconst arrayLength = array.length >>> 0;\n\n\t\t\tfor (let index = 0; index < arrayLength; index++) {\n\t\t\t\tif (!hasOwn(array, index)) continue;\n\t\t\t\tif (!callback.call(thisArg, array[index], index, array)) continue;\n\t\t\t\treturn array[index];\n\t\t\t}\n\n\t\t\treturn undefined;\n\t\t},\n\t\tconfigurable: true,\n\t\twritable: true\n\t});\n}\n","// NOTE: Node doesn't exist in IE8. Nothing can be done.\n/* istanbul ignore if */\nif (typeof window !== 'undefined' && window.Node && window.Node.prototype && !window.Node.prototype.contains) {\n\tNode.prototype.contains = function (node) {\n\t\tif (!node)\n\t\t\tthrow new TypeError('node required');\n\n\t\tdo {\n\t\t\tif (this === node) return true;\n\t\t} while (node = node && node.parentNode);\n\n\t\treturn false;\n\t};\n}\n","/* istanbul ignore if */\nif (typeof window !== 'undefined' && window.performance && !window.performance.now) {\n\twindow.performance = window.performance || {};\n\n\tconst nowOffset = Date.now();\n\n\twindow.performance.now = function () {\n\t\treturn Date.now() - nowOffset;\n\t};\n}\n","import { isFunction, isObjectType } from 'utils/is';\n\n/* istanbul ignore if */\nif (typeof window !== 'undefined' && !window.Promise) {\n\tconst PENDING = {};\n\tconst FULFILLED = {};\n\tconst REJECTED = {};\n\n\tconst Promise = window.Promise = function (callback) {\n\t\tconst fulfilledHandlers = [];\n\t\tconst rejectedHandlers = [];\n\t\tlet state = PENDING;\n\t\tlet result;\n\t\tlet dispatchHandlers;\n\n\t\tconst makeResolver = (newState) => {\n\t\t\treturn function (value) {\n\t\t\t\tif (state !== PENDING) return;\n\t\t\t\tresult = value;\n\t\t\t\tstate = newState;\n\t\t\t\tdispatchHandlers = makeDispatcher((state === FULFILLED ? fulfilledHandlers : rejectedHandlers), result);\n\t\t\t\twait(dispatchHandlers);\n\t\t\t};\n\t\t};\n\n\t\tconst fulfill = makeResolver(FULFILLED);\n\t\tconst reject = makeResolver(REJECTED);\n\n\t\ttry {\n\t\t\tcallback(fulfill, reject);\n\t\t} catch (err) {\n\t\t\treject(err);\n\t\t}\n\n\t\treturn {\n\t\t\t// `then()` returns a Promise - 2.2.7\n\t\t\tthen(onFulfilled, onRejected) {\n\t\t\t\tconst promise2 = new Promise((fulfill, reject) => {\n\n\t\t\t\t\tconst processResolutionHandler = (handler, handlers, forward) => {\n\t\t\t\t\t\tif (isFunction( handler )) {\n\t\t\t\t\t\t\thandlers.push(p1result => {\n\t\t\t\t\t\t\t\ttry {\n\t\t\t\t\t\t\t\t\tresolve(promise2, handler(p1result), fulfill, reject);\n\t\t\t\t\t\t\t\t} catch (err) {\n\t\t\t\t\t\t\t\t\treject(err);\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t});\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\thandlers.push(forward);\n\t\t\t\t\t\t}\n\t\t\t\t\t};\n\n\t\t\t\t\tprocessResolutionHandler(onFulfilled, fulfilledHandlers, fulfill);\n\t\t\t\t\tprocessResolutionHandler(onRejected, rejectedHandlers, reject);\n\n\t\t\t\t\tif (state !== PENDING) {\n\t\t\t\t\t\twait(dispatchHandlers);\n\t\t\t\t\t}\n\n\t\t\t\t});\n\t\t\t\treturn promise2;\n\t\t\t},\n\t\t\t'catch'(onRejected) {\n\t\t\t\treturn this.then(null, onRejected);\n\t\t\t}\n\t\t};\n\t};\n\n\tPromise.all = function (promises) {\n\t\treturn new Promise((fulfil, reject) => {\n\t\t\tconst result = [];\n\t\t\tlet pending;\n\t\t\tlet i;\n\n\t\t\tif (!promises.length) {\n\t\t\t\tfulfil(result);\n\t\t\t\treturn;\n\t\t\t}\n\n\t\t\tconst processPromise = (promise, i) => {\n\t\t\t\tif (promise && isFunction( promise.then )) {\n\t\t\t\t\tpromise.then(value => {\n\t\t\t\t\t\tresult[i] = value;\n\t\t\t\t\t\t--pending || fulfil(result);\n\t\t\t\t\t}, reject);\n\t\t\t\t} else {\n\t\t\t\t\tresult[i] = promise;\n\t\t\t\t\t--pending || fulfil(result);\n\t\t\t\t}\n\t\t\t};\n\n\t\t\tpending = i = promises.length;\n\n\t\t\twhile (i--) {\n\t\t\t\tprocessPromise(promises[i], i);\n\t\t\t}\n\t\t});\n\t};\n\n\tPromise.resolve = function (value) {\n\t\treturn new Promise(fulfill => {\n\t\t\tfulfill(value);\n\t\t});\n\t};\n\n\tPromise.reject = function (reason) {\n\t\treturn new Promise((fulfill, reject) => {\n\t\t\treject(reason);\n\t\t});\n\t};\n\n\t// TODO use MutationObservers or something to simulate setImmediate\n\tconst wait = function (callback) {\n\t\tsetTimeout(callback, 0);\n\t};\n\n\tconst makeDispatcher = function (handlers, result) {\n\t\treturn function () {\n\t\t\tfor (let handler; handler = handlers.shift();) {\n\t\t\t\thandler(result);\n\t\t\t}\n\t\t};\n\t};\n\n\tconst resolve = function (promise, x, fulfil, reject) {\n\t\tlet then;\n\t\tif (x === promise) {\n\t\t\tthrow new TypeError(`A promise's fulfillment handler cannot return the same promise`);\n\t\t}\n\t\tif (x instanceof Promise) {\n\t\t\tx.then(fulfil, reject);\n\t\t} else if (x && (isObjectType( x ) || isFunction( x ))) {\n\t\t\ttry {\n\t\t\t\tthen = x.then;\n\t\t\t} catch (e) {\n\t\t\t\treject(e);\n\t\t\t\treturn;\n\t\t\t}\n\t\t\tif (isFunction( then )) {\n\t\t\t\tlet called;\n\n\t\t\t\tconst resolvePromise = function (y) {\n\t\t\t\t\tif (called) return;\n\t\t\t\t\tcalled = true;\n\t\t\t\t\tresolve(promise, y, fulfil, reject);\n\t\t\t\t};\n\t\t\t\tconst rejectPromise = function (r) {\n\t\t\t\t\tif (called) return;\n\t\t\t\t\tcalled = true;\n\t\t\t\t\treject(r);\n\t\t\t\t};\n\n\t\t\t\ttry {\n\t\t\t\t\tthen.call(x, resolvePromise, rejectPromise);\n\t\t\t\t} catch (e) {\n\t\t\t\t\tif (!called) {\n\t\t\t\t\t\treject(e);\n\t\t\t\t\t\tcalled = true;\n\t\t\t\t\t\treturn;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tfulfil(x);\n\t\t\t}\n\t\t} else {\n\t\t\tfulfil(x);\n\t\t}\n\t};\n\n}\n","/* istanbul ignore if */\nif (typeof window !== 'undefined' && !(window.requestAnimationFrame && window.cancelAnimationFrame)) {\n\tlet lastTime = 0;\n\twindow.requestAnimationFrame = function (callback) {\n\t\tconst currentTime = Date.now();\n\t\tconst timeToNextCall = Math.max(0, 16 - (currentTime - lastTime));\n\t\tconst id = window.setTimeout(() => { callback(currentTime + timeToNextCall); }, timeToNextCall);\n\t\tlastTime = currentTime + timeToNextCall;\n\t\treturn id;\n\t};\n\twindow.cancelAnimationFrame = function (id) {\n\t\tclearTimeout(id);\n\t};\n}\n","export default {\n\t// render placement:\n\tel: void 0,\n\tappend: false,\n\tdelegate: true,\n\n\t// template:\n\ttemplate: null,\n\n\t// parse:\n\tallowExpressions: true,\n\tdelimiters: [ '{{', '}}' ],\n\ttripleDelimiters: [ '{{{', '}}}' ],\n\tstaticDelimiters: [ '[[', ']]' ],\n\tstaticTripleDelimiters: [ '[[[', ']]]' ],\n\tcsp: true,\n\tinterpolate: false,\n\tpreserveWhitespace: false,\n\tsanitize: false,\n\tstripComments: true,\n\tcontextLines: 0,\n\n\t// data & binding:\n\tdata: {},\n\tcomputed: {},\n\tsyncComputedChildren: false,\n\tresolveInstanceMembers: true,\n\twarnAboutAmbiguity: false,\n\tadapt: [],\n\tisolated: true,\n\ttwoway: true,\n\tlazy: false,\n\n\t// transitions:\n\tnoIntro: false,\n\tnoOutro: false,\n\ttransitionsEnabled: true,\n\tcomplete: void 0,\n\tnestedTransitions: true,\n\n\t// css:\n\tcss: null,\n\tnoCssTransform: false\n};\n","// These are a subset of the easing equations found at\n// https://raw.github.com/danro/easing-js - license info\n// follows:\n\n// --------------------------------------------------\n// easing.js v0.5.4\n// Generic set of easing functions with AMD support\n// https://github.com/danro/easing-js\n// This code may be freely distributed under the MIT license\n// http://danro.mit-license.org/\n// --------------------------------------------------\n// All functions adapted from Thomas Fuchs & Jeremy Kahn\n// Easing Equations (c) 2003 Robert Penner, BSD license\n// https://raw.github.com/danro/easing-js/master/LICENSE\n// --------------------------------------------------\n\n// In that library, the functions named easeIn, easeOut, and\n// easeInOut below are named easeInCubic, easeOutCubic, and\n// (you guessed it) easeInOutCubic.\n//\n// You can add additional easing functions to this list, and they\n// will be globally available.\n\n\nexport default {\n\tlinear ( pos ) { return pos; },\n\teaseIn ( pos ) {\n\t\t/* istanbul ignore next */\n\t\treturn Math.pow( pos, 3 );\n\t},\n\teaseOut ( pos ) { return ( Math.pow( ( pos - 1 ), 3 ) + 1 ); },\n\teaseInOut ( pos ) {\n\t\t/* istanbul ignore next */\n\t\tif ( ( pos /= 0.5 ) < 1 ) { return ( 0.5 * Math.pow( pos, 3 ) ); }\n\t\t/* istanbul ignore next */\n\t\treturn ( 0.5 * ( Math.pow( ( pos - 2 ), 3 ) + 2 ) );\n\t}\n};\n","/* eslint no-console:\"off\" */\nimport { isFunction } from 'utils/is';\n\nconst win = typeof window !== 'undefined' ? window : null;\nconst doc = win ? document : null;\nconst isClient = !!doc;\nconst hasConsole = ( typeof console !== 'undefined' && isFunction( console.warn ) && isFunction( console.warn.apply ) );\n\nconst svg = doc ?\n\tdoc.implementation.hasFeature( 'http://www.w3.org/TR/SVG11/feature#BasicStructure', '1.1' ) :\n\tfalse;\n\nconst vendors = [ 'o', 'ms', 'moz', 'webkit' ];\n\nexport { win, doc, isClient, hasConsole, svg, vendors };\n","export default function () {}\n","/* global console */\n/* eslint no-console:\"off\" */\n\nimport { hasConsole } from '../config/environment';\nimport Ractive from '../Ractive';\nimport noop from './noop';\nimport { isObjectType } from 'utils/is';\n\nconst alreadyWarned = {};\nlet log, printWarning, welcome;\n\nif ( hasConsole ) {\n\tconst welcomeIntro = [\n\t\t`%cRactive.js %c1.0.0-edge %cin debug mode, %cmore...`,\n\t\t'color: rgb(114, 157, 52); font-weight: normal;',\n\t\t'color: rgb(85, 85, 85); font-weight: normal;',\n\t\t'color: rgb(85, 85, 85); font-weight: normal;',\n\t\t'color: rgb(82, 140, 224); font-weight: normal; text-decoration: underline;'\n\t];\n\tconst welcomeMessage = `You're running Ractive 1.0.0-edge in debug mode - messages will be printed to the console to help you fix problems and optimise your application.\n\nTo disable debug mode, add this line at the start of your app:\n Ractive.DEBUG = false;\n\nTo disable debug mode when your app is minified, add this snippet:\n Ractive.DEBUG = /unminified/.test(function(){/*unminified*/});\n\nGet help and support:\n http://docs.ractivejs.org\n http://stackoverflow.com/questions/tagged/ractivejs\n http://groups.google.com/forum/#!forum/ractive-js\n http://twitter.com/ractivejs\n\nFound a bug? Raise an issue:\n https://github.com/ractivejs/ractive/issues\n\n`;\n\n\twelcome = () => {\n\t\tif ( Ractive.WELCOME_MESSAGE === false ) {\n\t\t\twelcome = noop;\n\t\t\treturn;\n\t\t}\n\t\tconst message = 'WELCOME_MESSAGE' in Ractive ? Ractive.WELCOME_MESSAGE : welcomeMessage;\n\t\tconst hasGroup = !!console.groupCollapsed;\n\t\tif ( hasGroup ) console.groupCollapsed.apply( console, welcomeIntro );\n\t\tconsole.log( message );\n\t\tif ( hasGroup ) {\n\t\t\tconsole.groupEnd( welcomeIntro );\n\t\t}\n\n\t\twelcome = noop;\n\t};\n\n\tprintWarning = ( message, args ) => {\n\t\twelcome();\n\n\t\t// extract information about the instance this message pertains to, if applicable\n\t\tif ( isObjectType( args[ args.length - 1 ] ) ) {\n\t\t\tconst options = args.pop();\n\t\t\tconst ractive = options ? options.ractive : null;\n\n\t\t\tif ( ractive ) {\n\t\t\t\t// if this is an instance of a component that we know the name of, add\n\t\t\t\t// it to the message\n\t\t\t\tlet name;\n\t\t\t\tif ( ractive.component && ( name = ractive.component.name ) ) {\n\t\t\t\t\tmessage = `<${name}> ${message}`;\n\t\t\t\t}\n\n\t\t\t\tlet node;\n\t\t\t\tif ( node = ( options.node || ( ractive.fragment && ractive.fragment.rendered && ractive.find( '*' ) ) ) ) {\n\t\t\t\t\targs.push( node );\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\tconsole.warn.apply( console, [ '%cRactive.js: %c' + message, 'color: rgb(114, 157, 52);', 'color: rgb(85, 85, 85);' ].concat( args ) );\n\t};\n\n\tlog = function () {\n\t\tconsole.log.apply( console, arguments );\n\t};\n} else {\n\tprintWarning = log = welcome = noop;\n}\n\nfunction format ( message, args ) {\n\treturn message.replace( /%s/g, () => args.shift() );\n}\n\nfunction fatal ( message, ...args ) {\n\tmessage = format( message, args );\n\tthrow new Error( message );\n}\n\nfunction logIfDebug () {\n\tif ( Ractive.DEBUG ) {\n\t\tlog.apply( null, arguments );\n\t}\n}\n\nfunction warn ( message, ...args ) {\n\tmessage = format( message, args );\n\tprintWarning( message, args );\n}\n\nfunction warnOnce ( message, ...args ) {\n\tmessage = format( message, args );\n\n\tif ( alreadyWarned[ message ] ) {\n\t\treturn;\n\t}\n\n\talreadyWarned[ message ] = true;\n\tprintWarning( message, args );\n}\n\nfunction warnIfDebug () {\n\tif ( Ractive.DEBUG ) {\n\t\twarn.apply( null, arguments );\n\t}\n}\n\nfunction warnOnceIfDebug () {\n\tif ( Ractive.DEBUG ) {\n\t\twarnOnce.apply( null, arguments );\n\t}\n}\n\nexport { fatal, log, logIfDebug, warn, warnOnce, warnIfDebug, warnOnceIfDebug, welcome };\n","// Error messages that are used (or could be) in multiple places\nexport const badArguments = 'Bad arguments';\nexport const noRegistryFunctionReturn = 'A function was specified for \"%s\" %s, but no %s was returned';\nexport const missingPlugin = ( name, type ) => `Missing \"${name}\" ${type} plugin. You may need to download a plugin via http://docs.ractivejs.org/latest/plugins#${type}s`;\n","export function findInViewHierarchy ( registryName, ractive, name ) {\n\tconst instance = findInstance( registryName, ractive, name );\n\treturn instance ? instance[ registryName ][ name ] : null;\n}\n\nexport function findInstance ( registryName, ractive, name ) {\n\twhile ( ractive ) {\n\t\tif ( name in ractive[ registryName ] ) {\n\t\t\treturn ractive;\n\t\t}\n\n\t\tif ( ractive.isolated ) {\n\t\t\treturn null;\n\t\t}\n\n\t\tractive = ractive.parent;\n\t}\n}","import { fatal } from 'utils/log';\nimport { missingPlugin } from 'config/errors';\nimport interpolators from '../Ractive/static/interpolators';\nimport { findInViewHierarchy } from './registry';\n\nexport default function interpolate ( from, to, ractive, type ) {\n\tif ( from === to ) return null;\n\n\tif ( type ) {\n\t\tconst interpol = findInViewHierarchy( 'interpolators', ractive, type );\n\t\tif ( interpol ) return interpol( from, to ) || null;\n\n\t\tfatal( missingPlugin( type, 'interpolator' ) );\n\t}\n\n\treturn interpolators.number( from, to ) ||\n\t interpolators.array( from, to ) ||\n\t interpolators.object( from, to ) ||\n\t null;\n}\n","import { isArray, isObject, isNumeric } from 'utils/is';\nimport interpolate from 'shared/interpolate';\nimport { hasOwn } from 'utils/object';\n\nconst interpolators = {\n\tnumber ( from, to ) {\n\t\tif ( !isNumeric( from ) || !isNumeric( to ) ) {\n\t\t\treturn null;\n\t\t}\n\n\t\tfrom = +from;\n\t\tto = +to;\n\n\t\tconst delta = to - from;\n\n\t\tif ( !delta ) {\n\t\t\treturn function () { return from; };\n\t\t}\n\n\t\treturn function ( t ) {\n\t\t\treturn from + ( t * delta );\n\t\t};\n\t},\n\n\tarray ( from, to ) {\n\t\tlet len, i;\n\n\t\tif ( !isArray( from ) || !isArray( to ) ) {\n\t\t\treturn null;\n\t\t}\n\n\t\tconst intermediate = [];\n\t\tconst interpolators = [];\n\n\t\ti = len = Math.min( from.length, to.length );\n\t\twhile ( i-- ) {\n\t\t\tinterpolators[i] = interpolate( from[i], to[i] );\n\t\t}\n\n\t\t// surplus values - don't interpolate, but don't exclude them either\n\t\tfor ( i=len; i to[ prop ] );\n\t\t\t\t}\n\n\t\t\t\telse {\n\t\t\t\t\tintermediate[ prop ] = from[ prop ];\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\tfor ( const prop in to ) {\n\t\t\tif ( hasOwn( to, prop ) && !hasOwn( from, prop ) ) {\n\t\t\t\tintermediate[ prop ] = to[ prop ];\n\t\t\t}\n\t\t}\n\n\t\tconst len = properties.length;\n\n\t\treturn function ( t ) {\n\t\t\tlet i = len;\n\n\t\t\twhile ( i-- ) {\n\t\t\t\tconst prop = properties[i];\n\n\t\t\t\tintermediate[ prop ] = interpolators[ prop ]( t );\n\t\t\t}\n\n\t\t\treturn intermediate;\n\t\t};\n\t}\n};\n\nexport default interpolators;\n","import { isString } from 'utils/is';\n\nconst refPattern = /\\[\\s*(\\*|[0-9]|[1-9][0-9]+)\\s*\\]/g;\nconst splitPattern = /([^\\\\](?:\\\\\\\\)*)\\./;\nconst escapeKeyPattern = /\\\\|\\./g;\nconst unescapeKeyPattern = /((?:\\\\)+)\\1|\\\\(\\.)/g;\n\nexport function escapeKey ( key ) {\n\tif ( isString( key ) ) {\n\t\treturn key.replace( escapeKeyPattern, '\\\\$&' );\n\t}\n\n\treturn key;\n}\n\nexport function normalise ( ref ) {\n\treturn ref ? ref.replace( refPattern, '.$1' ) : '';\n}\n\nexport function splitKeypath ( keypath ) {\n\tconst result = [];\n\tlet match;\n\n\tkeypath = normalise( keypath );\n\n\twhile ( match = splitPattern.exec( keypath ) ) {\n\t\tconst index = match.index + match[1].length;\n\t\tresult.push( keypath.substr( 0, index ) );\n\t\tkeypath = keypath.substr( index + 1 );\n\t}\n\n\tresult.push( keypath );\n\n\treturn result;\n}\n\nexport function unescapeKey ( key ) {\n\tif ( isString( key ) ) {\n\t\treturn key.replace( unescapeKeyPattern, '$1$2' );\n\t}\n\n\treturn key;\n}\n","import { isArray, isString } from './is';\n\nexport function addToArray ( array, value ) {\n\tconst index = array.indexOf( value );\n\n\tif ( index === -1 ) {\n\t\tarray.push( value );\n\t}\n}\n\nexport function arrayContains ( array, value ) {\n\tfor ( let i = 0, c = array.length; i < c; i++ ) {\n\t\tif ( array[i] == value ) {\n\t\t\treturn true;\n\t\t}\n\t}\n\n\treturn false;\n}\n\nexport function arrayContentsMatch ( a, b ) {\n\tlet i;\n\n\tif ( !isArray( a ) || !isArray( b ) ) {\n\t\treturn false;\n\t}\n\n\tif ( a.length !== b.length ) {\n\t\treturn false;\n\t}\n\n\ti = a.length;\n\twhile ( i-- ) {\n\t\tif ( a[i] !== b[i] ) {\n\t\t\treturn false;\n\t\t}\n\t}\n\n\treturn true;\n}\n\nexport function ensureArray ( x ) {\n\tif ( isString( x ) ) {\n\t\treturn [ x ];\n\t}\n\n\tif ( x === undefined ) {\n\t\treturn [];\n\t}\n\n\treturn x;\n}\n\nexport function lastItem ( array ) {\n\treturn array[ array.length - 1 ];\n}\n\nexport function removeFromArray ( array, member ) {\n\tif ( !array ) {\n\t\treturn;\n\t}\n\n\tconst index = array.indexOf( member );\n\n\tif ( index !== -1 ) {\n\t\tarray.splice( index, 1 );\n\t}\n}\n\nexport function combine ( ...arrays ) {\n\tconst res = arrays.concat.apply( [], arrays );\n\tlet i = res.length;\n\twhile ( i-- ) {\n\t\tconst idx = res.indexOf( res[i] );\n\t\tif ( ~idx && idx < i ) res.splice( i, 1 );\n\t}\n\n\treturn res;\n}\n\nexport function toArray ( arrayLike ) {\n\tconst array = [];\n\tlet i = arrayLike.length;\n\twhile ( i-- ) {\n\t\tarray[i] = arrayLike[i];\n\t}\n\n\treturn array;\n}\n\nexport function findMap ( array, fn ) {\n\tconst len = array.length;\n\tfor ( let i = 0; i < len; i++ ) {\n\t\tconst result = fn( array[i] );\n\t\tif ( result ) return result;\n\t}\n}\n","const stack = [];\nlet captureGroup;\n\nexport function startCapturing () {\n\tstack.push( captureGroup = [] );\n}\n\nexport function stopCapturing () {\n\tconst dependencies = stack.pop();\n\tcaptureGroup = stack[ stack.length - 1 ];\n\treturn dependencies;\n}\n\nexport function capture ( model ) {\n\tif ( captureGroup ) {\n\t\tcaptureGroup.push( model );\n\t}\n}\n","import { addToArray, removeFromArray } from 'utils/array';\nimport { unescapeKey } from 'shared/keypaths';\nimport { capture } from 'src/global/capture';\nimport noop from 'utils/noop';\n\nexport default class KeyModel {\n\tconstructor ( key, parent ) {\n\t\tthis.value = key;\n\t\tthis.isReadonly = this.isKey = true;\n\t\tthis.deps = [];\n\t\tthis.links = [];\n\t\tthis.parent = parent;\n\t}\n\n\tget ( shouldCapture ) {\n\t\tif ( shouldCapture ) capture( this );\n\t\treturn unescapeKey( this.value );\n\t}\n\n\tgetKeypath () {\n\t\treturn unescapeKey( this.value );\n\t}\n\n\trebind ( next, previous ) {\n\t\tlet i = this.deps.length;\n\t\twhile ( i-- ) this.deps[i].rebind( next, previous, false );\n\n\t\ti = this.links.length;\n\t\twhile ( i-- ) this.links[i].relinking( next, false );\n\t}\n\n\tregister ( dependant ) {\n\t\tthis.deps.push( dependant );\n\t}\n\n\tregisterLink ( link ) {\n\t\taddToArray( this.links, link );\n\t}\n\n\tunregister ( dependant ) {\n\t\tremoveFromArray( this.deps, dependant );\n\t}\n\n\tunregisterLink ( link ) {\n\t\tremoveFromArray( this.links, link );\n\t}\n}\n\nKeyModel.prototype.reference = noop;\nKeyModel.prototype.unreference = noop;\n","export function bind ( x ) { x.bind(); }\nexport function cancel ( x ) { x.cancel(); }\nexport function destroyed ( x ) { x.destroyed(); }\nexport function handleChange ( x ) { x.handleChange(); }\nexport function mark ( x ) { x.mark(); }\nexport function markForce ( x ) { x.mark( true ); }\nexport function marked ( x ) { x.marked(); }\nexport function markedAll ( x ) { x.markedAll(); }\nexport function render ( x ) { x.render(); }\nexport function shuffled ( x ) { x.shuffled(); }\nexport function teardown ( x ) { x.teardown(); }\nexport function unbind ( x ) { x.unbind(); }\nexport function unrender ( x ) { x.unrender(); }\nexport function unrenderAndDestroy ( x ) { x.unrender( true ); }\nexport function update ( x ) { x.update(); }\nexport function toString ( x ) { return x.toString(); }\nexport function toEscapedString ( x ) { return x.toString( true ); }\n","import { removeFromArray } from 'utils/array';\nimport { handleChange } from 'shared/methodCallers';\nimport { capture } from 'src/global/capture';\nimport noop from 'utils/noop';\nimport { keys as objectKeys } from 'utils/object';\n\nexport default class KeypathModel {\n\tconstructor ( parent, ractive ) {\n\t\tthis.parent = parent;\n\t\tthis.ractive = ractive;\n\t\tthis.value = ractive ? parent.getKeypath( ractive ) : parent.getKeypath();\n\t\tthis.deps = [];\n\t\tthis.children = {};\n\t\tthis.isReadonly = this.isKeypath = true;\n\t}\n\n\tget ( shouldCapture ) {\n\t\tif ( shouldCapture ) capture( this );\n\t\treturn this.value;\n\t}\n\n\tgetChild ( ractive ) {\n\t\tif ( !( ractive._guid in this.children ) ) {\n\t\t\tconst model = new KeypathModel( this.parent, ractive );\n\t\t\tthis.children[ ractive._guid ] = model;\n\t\t\tmodel.owner = this;\n\t\t}\n\t\treturn this.children[ ractive._guid ];\n\t}\n\n\tgetKeypath () {\n\t\treturn this.value;\n\t}\n\n\thandleChange () {\n\t\tconst keys = objectKeys( this.children );\n\t\tlet i = keys.length;\n\t\twhile ( i-- ) {\n\t\t\tthis.children[ keys[i] ].handleChange();\n\t\t}\n\n\t\tthis.deps.forEach( handleChange );\n\t}\n\n\trebindChildren ( next ) {\n\t\tconst keys = objectKeys( this.children );\n\t\tlet i = keys.length;\n\t\twhile ( i-- ) {\n\t\t\tconst child = this.children[keys[i]];\n\t\t\tchild.value = next.getKeypath( child.ractive );\n\t\t\tchild.handleChange();\n\t\t}\n\t}\n\n\trebind ( next, previous ) {\n\t\tconst model = next ? next.getKeypathModel( this.ractive ) : undefined;\n\n\t\tconst keys = objectKeys( this.children );\n\t\tlet i = keys.length;\n\t\twhile ( i-- ) {\n\t\t\tthis.children[ keys[i] ].rebind( next, previous, false );\n\t\t}\n\n\t\ti = this.deps.length;\n\t\twhile ( i-- ) {\n\t\t\tthis.deps[i].rebind( model, this, false );\n\t\t}\n\t}\n\n\tregister ( dep ) {\n\t\tthis.deps.push( dep );\n\t}\n\n\tremoveChild( model ) {\n\t\tif ( model.ractive ) delete this.children[ model.ractive._guid ];\n\t}\n\n\tteardown () {\n\t\tif ( this.owner ) this.owner.removeChild( this );\n\n\t\tconst keys = objectKeys( this.children );\n\t\tlet i = keys.length;\n\t\twhile ( i-- ) {\n\t\t\tthis.children[ keys[i] ].teardown();\n\t\t}\n\t}\n\n\tunregister ( dep ) {\n\t\tremoveFromArray( this.deps, dep );\n\t\tif ( !this.deps.length ) this.teardown();\n\t}\n}\n\nKeypathModel.prototype.reference = noop;\nKeypathModel.prototype.unreference = noop;\n","const fnBind = Function.prototype.bind;\n\nexport default function bind ( fn, context ) {\n\tif ( !/this/.test( fn.toString() ) ) return fn;\n\n\tconst bound = fnBind.call( fn, context );\n\tfor ( const prop in fn ) bound[ prop ] = fn[ prop ];\n\n\treturn bound;\n}\n","import KeyModel from './specials/KeyModel';\nimport KeypathModel from './specials/KeypathModel';\nimport { escapeKey, unescapeKey } from 'shared/keypaths';\nimport { addToArray, removeFromArray } from 'utils/array';\nimport { isArray, isObject, isFunction } from 'utils/is';\nimport bind from 'utils/bind';\nimport { hasOwn, keys as objectKeys } from 'utils/object';\n\nconst shuffleTasks = { early: [], mark: [] };\nconst registerQueue = { early: [], mark: [] };\n\nexport default class ModelBase {\n\tconstructor ( parent ) {\n\t\tthis.deps = [];\n\n\t\tthis.children = [];\n\t\tthis.childByKey = {};\n\t\tthis.links = [];\n\n\t\tthis.keyModels = {};\n\n\t\tthis.bindings = [];\n\t\tthis.patternObservers = [];\n\n\t\tif ( parent ) {\n\t\t\tthis.parent = parent;\n\t\t\tthis.root = parent.root;\n\t\t}\n\t}\n\n\taddShuffleTask ( task, stage = 'early' ) { shuffleTasks[stage].push( task ); }\n\taddShuffleRegister ( item, stage = 'early' ) { registerQueue[stage].push({ model: this, item }); }\n\n\tdownstreamChanged () {}\n\n\tfindMatches ( keys ) {\n\t\tconst len = keys.length;\n\n\t\tlet existingMatches = [ this ];\n\t\tlet matches;\n\t\tlet i;\n\n\t\tfor ( i = 0; i < len; i += 1 ) {\n\t\t\tconst key = keys[i];\n\n\t\t\tif ( key === '*' ) {\n\t\t\t\tmatches = [];\n\t\t\t\texistingMatches.forEach( model => {\n\t\t\t\t\tmatches.push.apply( matches, model.getValueChildren( model.get() ) );\n\t\t\t\t});\n\t\t\t} else {\n\t\t\t\tmatches = existingMatches.map( model => model.joinKey( key ) );\n\t\t\t}\n\n\t\t\texistingMatches = matches;\n\t\t}\n\n\t\treturn matches;\n\t}\n\n\tgetKeyModel ( key, skip ) {\n\t\tif ( key !== undefined && !skip ) return this.parent.getKeyModel( key, true );\n\n\t\tif ( !( key in this.keyModels ) ) this.keyModels[ key ] = new KeyModel( escapeKey( key ), this );\n\n\t\treturn this.keyModels[ key ];\n\t}\n\n\tgetKeypath ( ractive ) {\n\t\tif ( ractive !== this.ractive && this._link ) return this._link.target.getKeypath( ractive );\n\n\t\tif ( !this.keypath ) {\n\t\t\tconst parent = this.parent && this.parent.getKeypath( ractive );\n\t\t\tthis.keypath = parent ? `${this.parent.getKeypath( ractive )}.${escapeKey( this.key )}` : escapeKey( this.key );\n\t\t}\n\n\t\treturn this.keypath;\n\t}\n\n\tgetValueChildren ( value ) {\n\t\tlet children;\n\t\tif ( isArray( value ) ) {\n\t\t\tchildren = [];\n\t\t\tif ( 'length' in this && this.length !== value.length ) {\n\t\t\t\tchildren.push( this.joinKey( 'length' ) );\n\t\t\t}\n\t\t\tvalue.forEach( ( m, i ) => {\n\t\t\t\tchildren.push( this.joinKey( i ) );\n\t\t\t});\n\t\t}\n\n\t\telse if ( isObject( value ) || isFunction( value ) ) {\n\t\t\tchildren = objectKeys( value ).map( key => this.joinKey( key ) );\n\t\t}\n\n\t\telse if ( value != null ) {\n\t\t\treturn [];\n\t\t}\n\n\t\treturn children;\n\t}\n\n\tgetVirtual ( shouldCapture ) {\n\t\tconst value = this.get( shouldCapture, { virtual: false } );\n\t\tif ( isObject( value ) ) {\n\t\t\tconst result = isArray( value ) ? [] : {};\n\n\t\t\tconst keys = objectKeys( value );\n\t\t\tlet i = keys.length;\n\t\t\twhile ( i-- ) {\n\t\t\t\tconst child = this.childByKey[ keys[i] ];\n\t\t\t\tif ( !child ) result[ keys[i] ] = value[ keys[i] ];\n\t\t\t\telse if ( child._link ) result[ keys[i] ] = child._link.getVirtual();\n\t\t\t\telse result[ keys[i] ] = child.getVirtual();\n\t\t\t}\n\n\t\t\ti = this.children.length;\n\t\t\twhile ( i-- ) {\n\t\t\t\tconst child = this.children[i];\n\t\t\t\tif ( !( child.key in result ) && child._link ) {\n\t\t\t\t\tresult[ child.key ] = child._link.getVirtual();\n\t\t\t\t}\n\t\t\t}\n\n\t\t\treturn result;\n\t\t} else return value;\n\t}\n\n\thas ( key ) {\n\t\tif ( this._link ) return this._link.has( key );\n\n\t\tconst value = this.get();\n\t\tif ( !value ) return false;\n\n\t\tkey = unescapeKey( key );\n\t\tif ( hasOwn( value, key ) ) return true;\n\n\t\t// We climb up the constructor chain to find if one of them contains the key\n\t\tlet constructor = value.constructor;\n\t\twhile ( constructor !== Function && constructor !== Array && constructor !== Object ) {\n\t\t\tif ( hasOwn( constructor.prototype, key ) ) return true;\n\t\t\tconstructor = constructor.constructor;\n\t\t}\n\n\t\treturn false;\n\t}\n\n\tjoinAll ( keys, opts ) {\n\t\tlet model = this;\n\t\tfor ( let i = 0; i < keys.length; i += 1 ) {\n\t\t\tif ( opts && opts.lastLink === false && i + 1 === keys.length && model.childByKey[keys[i]] && model.childByKey[keys[i]]._link ) return model.childByKey[keys[i]];\n\t\t\tmodel = model.joinKey( keys[i], opts );\n\t\t}\n\n\t\treturn model;\n\t}\n\n\tnotifyUpstream ( startPath ) {\n\t\tlet parent = this.parent;\n\t\tconst path = startPath || [ this.key ];\n\t\twhile ( parent ) {\n\t\t\tif ( parent.patternObservers.length ) parent.patternObservers.forEach( o => o.notify( path.slice() ) );\n\t\t\tpath.unshift( parent.key );\n\t\t\tparent.links.forEach( l => l.notifiedUpstream( path, this.root ) );\n\t\t\tparent.deps.forEach( d => d.handleChange( path ) );\n\t\t\tparent.downstreamChanged( startPath );\n\t\t\tparent = parent.parent;\n\t\t}\n\t}\n\n\trebind ( next, previous, safe ) {\n\t\tif ( this._link ) {\n\t\t\tthis._link.rebind( next, previous, false );\n\t\t}\n\n\t\t// tell the deps to move to the new target\n\t\tlet i = this.deps.length;\n\t\twhile ( i-- ) {\n\t\t\tif ( this.deps[i].rebind ) this.deps[i].rebind( next, previous, safe );\n\t\t}\n\n\t\ti = this.links.length;\n\t\twhile ( i-- ) {\n\t\t\tconst link = this.links[i];\n\t\t\t// only relink the root of the link tree\n\t\t\tif ( link.owner._link ) link.relinking( next, safe );\n\t\t}\n\n\t\ti = this.children.length;\n\t\twhile ( i-- ) {\n\t\t\tconst child = this.children[i];\n\t\t\tchild.rebind( next ? next.joinKey( child.key ) : undefined, child, safe );\n\t\t}\n\n\t\tif ( this.keypathModel ) this.keypathModel.rebind( next, previous, false );\n\n\t\ti = this.bindings.length;\n\t\twhile ( i-- ) {\n\t\t\tthis.bindings[i].rebind( next, previous, safe );\n\t\t}\n\t}\n\n\treference () {\n\t\t'refs' in this ? this.refs++ : this.refs = 1;\n\t}\n\n\tregister ( dep ) {\n\t\tthis.deps.push( dep );\n\t}\n\n\tregisterLink ( link ) {\n\t\taddToArray( this.links, link );\n\t}\n\n\tregisterPatternObserver ( observer ) {\n\t\tthis.patternObservers.push( observer );\n\t\tthis.register( observer );\n\t}\n\n\tregisterTwowayBinding ( binding ) {\n\t\tthis.bindings.push( binding );\n\t}\n\n\tunreference () {\n\t\tif ( 'refs' in this ) this.refs--;\n\t}\n\n\tunregister ( dep ) {\n\t\tremoveFromArray( this.deps, dep );\n\t}\n\n\tunregisterLink ( link ) {\n\t\tremoveFromArray( this.links, link );\n\t}\n\n\tunregisterPatternObserver ( observer ) {\n\t\tremoveFromArray( this.patternObservers, observer );\n\t\tthis.unregister( observer );\n\t}\n\n\tunregisterTwowayBinding ( binding ) {\n\t\tremoveFromArray( this.bindings, binding );\n\t}\n\n\tupdateFromBindings ( cascade ) {\n\t\tlet i = this.bindings.length;\n\t\twhile ( i-- ) {\n\t\t\tconst value = this.bindings[i].getValue();\n\t\t\tif ( value !== this.value ) this.set( value );\n\t\t}\n\n\t\t// check for one-way bindings if there are no two-ways\n\t\tif ( !this.bindings.length ) {\n\t\t\tconst oneway = findBoundValue( this.deps );\n\t\t\tif ( oneway && oneway.value !== this.value ) this.set( oneway.value );\n\t\t}\n\n\t\tif ( cascade ) {\n\t\t\tthis.children.forEach( updateFromBindings );\n\t\t\tthis.links.forEach( updateFromBindings );\n\t\t\tif ( this._link ) this._link.updateFromBindings( cascade );\n\t\t}\n\t}\n}\n\n// TODO: this may be better handled by overreiding `get` on models with a parent that isRoot\nexport function maybeBind ( model, value, shouldBind ) {\n\tif ( shouldBind && isFunction( value ) && model.parent && model.parent.isRoot ) {\n\t\tif ( !model.boundValue ) {\n\t\t\tmodel.boundValue = bind( value._r_unbound || value, model.parent.ractive );\n\t\t}\n\n\t\treturn model.boundValue;\n\t}\n\n\treturn value;\n}\n\nfunction updateFromBindings ( model ) {\n\tmodel.updateFromBindings( true );\n}\n\nexport function findBoundValue( list ) {\n\tlet i = list.length;\n\twhile ( i-- ) {\n\t\tif ( list[i].bound ) {\n\t\t\tconst owner = list[i].owner;\n\t\t\tif ( owner ) {\n\t\t\t\tconst value = owner.name === 'checked' ?\n\t\t\t\t\towner.node.checked :\n\t\t\t\t\towner.node.value;\n\t\t\t\treturn { value };\n\t\t\t}\n\t\t}\n\t}\n}\n\nexport function fireShuffleTasks ( stage ) {\n\tif ( !stage ) {\n\t\tfireShuffleTasks( 'early' );\n\t\tfireShuffleTasks( 'mark' );\n\t} else {\n\t\tconst tasks = shuffleTasks[stage];\n\t\tshuffleTasks[stage] = [];\n\t\tlet i = tasks.length;\n\t\twhile ( i-- ) tasks[i]();\n\n\t\tconst register = registerQueue[stage];\n\t\tregisterQueue[stage] = [];\n\t\ti = register.length;\n\t\twhile ( i-- ) register[i].model.register( register[i].item );\n\t}\n}\n\nexport function shuffle ( model, newIndices, link, unsafe ) {\n\tmodel.shuffling = true;\n\n\tlet i = newIndices.length;\n\twhile ( i-- ) {\n\t\tconst idx = newIndices[ i ];\n\t\t// nothing is actually changing, so move in the index and roll on\n\t\tif ( i === idx ) {\n\t\t\tcontinue;\n\t\t}\n\n\t\t// rebind the children on i to idx\n\t\tif ( i in model.childByKey ) model.childByKey[ i ].rebind( !~idx ? undefined : model.joinKey( idx ), model.childByKey[ i ], !unsafe );\n\n\t\tif ( !~idx && model.keyModels[ i ] ) {\n\t\t\tmodel.keyModels[i].rebind( undefined, model.keyModels[i], false );\n\t\t} else if ( ~idx && model.keyModels[ i ] ) {\n\t\t\tif ( !model.keyModels[ idx ] ) model.childByKey[ idx ].getKeyModel( idx );\n\t\t\tmodel.keyModels[i].rebind( model.keyModels[ idx ], model.keyModels[i], false );\n\t\t}\n\t}\n\n\tconst upstream = model.source().length !== model.source().value.length;\n\n\tmodel.links.forEach( l => l.shuffle( newIndices ) );\n\tif ( !link ) fireShuffleTasks( 'early' );\n\n\ti = model.deps.length;\n\twhile ( i-- ) {\n\t\tif ( model.deps[i].shuffle ) model.deps[i].shuffle( newIndices );\n\t}\n\n\tmodel[ link ? 'marked' : 'mark' ]();\n\tif ( !link ) fireShuffleTasks( 'mark' );\n\n\tif ( upstream ) model.notifyUpstream();\n\n\tmodel.shuffling = false;\n}\n\nKeyModel.prototype.addShuffleTask = ModelBase.prototype.addShuffleTask;\nKeyModel.prototype.addShuffleRegister = ModelBase.prototype.addShuffleRegister;\nKeypathModel.prototype.addShuffleTask = ModelBase.prototype.addShuffleTask;\nKeypathModel.prototype.addShuffleRegister = ModelBase.prototype.addShuffleRegister;\n","import { splitKeypath } from './keypaths';\nimport { isString } from 'utils/is';\n\n// this is the dry method of checking to see if a rebind applies to\n// a particular keypath because in some cases, a dep may be bound\n// directly to a particular keypath e.g. foo.bars.0.baz and need\n// to avoid getting kicked to foo.bars.1.baz if foo.bars is unshifted\nexport function rebindMatch ( template, next, previous, fragment ) {\n\tconst keypath = template.r || template;\n\n\t// no valid keypath, go with next\n\tif ( !keypath || !isString( keypath ) ) return next;\n\n\t// completely contextual ref, go with next\n\tif ( keypath === '.' || keypath[0] === '@' || ( next || previous ).isKey || ( next || previous ).isKeypath ) return next;\n\n\tconst parts = keypath.split( '/' );\n\tlet keys = splitKeypath( parts[ parts.length - 1 ] );\n\tconst last = keys[ keys.length - 1 ];\n\n\t// check the keypath against the model keypath to see if it matches\n\tlet model = next || previous;\n\n\t// check to see if this was an alias\n\tif ( model && keys.length === 1 && last !== model.key && fragment ) {\n\t\tkeys = findAlias( last, fragment ) || keys;\n\t}\n\n\tlet i = keys.length;\n\tlet match = true;\n\tlet shuffling = false;\n\n\twhile ( model && i-- ) {\n\t\tif ( model.shuffling ) shuffling = true;\n\t\t// non-strict comparison to account for indices in keypaths\n\t\tif ( keys[i] != model.key ) match = false;\n\t\tmodel = model.parent;\n\t}\n\n\t// next is undefined, but keypath is shuffling and previous matches\n\tif ( !next && match && shuffling ) return previous;\n\t// next is defined, but doesn't match the keypath\n\telse if ( next && !match && shuffling ) return previous;\n\telse return next;\n}\n\nfunction findAlias ( name, fragment ) {\n\twhile ( fragment ) {\n\t\tconst z = fragment.aliases;\n\t\tif ( z && z[ name ] ) {\n\t\t\tconst aliases = ( fragment.owner.iterations ? fragment.owner : fragment ).owner.template.z;\n\t\t\tfor ( let i = 0; i < aliases.length; i++ ) {\n\t\t\t\tif ( aliases[i].n === name ) {\n\t\t\t\t\tconst alias = aliases[i].x;\n\t\t\t\t\tif ( !alias.r ) return false;\n\t\t\t\t\tconst parts = alias.r.split( '/' );\n\t\t\t\t\treturn splitKeypath( parts[ parts.length - 1 ] );\n\t\t\t\t}\n\t\t\t}\n\t\t\treturn;\n\t\t}\n\n\t\tfragment = fragment.componentParent || fragment.parent;\n\t}\n}\n","import ModelBase, { fireShuffleTasks, maybeBind, shuffle } from './ModelBase';\nimport KeypathModel from './specials/KeypathModel';\nimport { capture } from '../global/capture';\nimport { handleChange, marked, markedAll, teardown } from 'shared/methodCallers';\nimport { rebindMatch } from 'shared/rebind';\nimport resolveReference from 'src/view/resolvers/resolveReference';\nimport noop from 'utils/noop';\nimport { hasOwn } from 'utils/object';\n\n// temporary placeholder target for detached implicit links\nexport const Missing = {\n\tkey: '@missing',\n\tanimate: noop,\n\tapplyValue: noop,\n\tget: noop,\n\tgetKeypath () { return this.key; },\n\tjoinAll () { return this; },\n\tjoinKey () { return this; },\n\tmark: noop,\n\tregisterLink: noop,\n\tshufle: noop,\n\tset: noop,\n\tunregisterLink: noop\n};\nMissing.parent = Missing;\n\nexport default class LinkModel extends ModelBase {\n\tconstructor ( parent, owner, target, key ) {\n\t\tsuper( parent );\n\n\t\tthis.owner = owner;\n\t\tthis.target = target;\n\t\tthis.key = key === undefined ? owner.key : key;\n\t\tif ( owner.isLink ) this.sourcePath = `${owner.sourcePath}.${this.key}`;\n\n\t\ttarget.registerLink( this );\n\n\t\tif ( parent ) this.isReadonly = parent.isReadonly;\n\n\t\tthis.isLink = true;\n\t}\n\n\tanimate ( from, to, options, interpolator ) {\n\t\treturn this.target.animate( from, to, options, interpolator );\n\t}\n\n\tapplyValue ( value ) {\n\t\tif ( this.boundValue ) this.boundValue = null;\n\t\tthis.target.applyValue( value );\n\t}\n\n\tattach ( fragment ) {\n\t\tconst model = resolveReference( fragment, this.key );\n\t\tif ( model ) {\n\t\t\tthis.relinking( model, false );\n\t\t} else { // if there is no link available, move everything here to real models\n\t\t\tthis.owner.unlink();\n\t\t}\n\t}\n\n\tdetach () {\n\t\tthis.relinking( Missing, false );\n\t}\n\n\tget ( shouldCapture, opts = {} ) {\n\t\tif ( shouldCapture ) {\n\t\t\tcapture( this );\n\n\t\t\t// may need to tell the target to unwrap\n\t\t\topts.unwrap = true;\n\t\t}\n\n\t\tconst bind = 'shouldBind' in opts ? opts.shouldBind : true;\n\t\topts.shouldBind = this.mapping && this.target.parent && this.target.parent.isRoot;\n\n\t\treturn maybeBind( this, this.target.get( false, opts ), bind );\n\t}\n\n\tgetKeypath ( ractive ) {\n\t\tif ( ractive && ractive !== this.root.ractive ) return this.target.getKeypath( ractive );\n\n\t\treturn super.getKeypath( ractive );\n\t}\n\n\tgetKeypathModel ( ractive ) {\n\t\tif ( !this.keypathModel ) this.keypathModel = new KeypathModel( this );\n\t\tif ( ractive && ractive !== this.root.ractive ) return this.keypathModel.getChild( ractive );\n\t\treturn this.keypathModel;\n\t}\n\n\thandleChange () {\n\t\tthis.deps.forEach( handleChange );\n\t\tthis.links.forEach( handleChange );\n\t\tthis.notifyUpstream();\n\t}\n\n\tisDetached () { return this.virtual && this.target === Missing; }\n\n\tjoinKey ( key ) {\n\t\t// TODO: handle nested links\n\t\tif ( key === undefined || key === '' ) return this;\n\n\t\tif ( !hasOwn( this.childByKey, key ) ) {\n\t\t\tconst child = new LinkModel( this, this, this.target.joinKey( key ), key );\n\t\t\tthis.children.push( child );\n\t\t\tthis.childByKey[ key ] = child;\n\t\t}\n\n\t\treturn this.childByKey[ key ];\n\t}\n\n\tmark ( force ) {\n\t\tthis.target.mark( force );\n\t}\n\n\tmarked () {\n\t\tif ( this.boundValue ) this.boundValue = null;\n\n\t\tthis.links.forEach( marked );\n\n\t\tthis.deps.forEach( handleChange );\n\t}\n\n\tmarkedAll () {\n\t\tthis.children.forEach( markedAll );\n\t\tthis.marked();\n\t}\n\n\tnotifiedUpstream ( startPath, root ) {\n\t\tthis.links.forEach( l => l.notifiedUpstream( startPath, this.root ) );\n\t\tthis.deps.forEach( handleChange );\n\t\tif ( startPath && this.rootLink && this.root !== root ) {\n\t\t\tconst path = startPath.slice( 1 );\n\t\t\tpath.unshift( this.key );\n\t\t\tthis.notifyUpstream( path );\n\t\t}\n\t}\n\n\trelinked () {\n\t\tthis.target.registerLink( this );\n\t\tthis.children.forEach( c => c.relinked() );\n\t}\n\n\trelinking ( target, safe ) {\n\t\tif ( this.rootLink && this.sourcePath ) target = rebindMatch( this.sourcePath, target, this.target );\n\t\tif ( !target || this.target === target ) return;\n\n\t\tthis.target.unregisterLink( this );\n\t\tif ( this.keypathModel ) this.keypathModel.rebindChildren( target );\n\n\t\tthis.target = target;\n\t\tthis.children.forEach( c => {\n\t\t\tc.relinking( target.joinKey( c.key ), safe );\n\t\t});\n\n\t\tif ( this.rootLink ) this.addShuffleTask( () => {\n\t\t\tthis.relinked();\n\t\t\tif ( !safe ) {\n\t\t\t\tthis.markedAll();\n\t\t\t\tthis.notifyUpstream();\n\t\t\t}\n\t\t});\n\t}\n\n\tset ( value ) {\n\t\tif ( this.boundValue ) this.boundValue = null;\n\t\tthis.target.set( value );\n\t}\n\n\tshuffle ( newIndices ) {\n\t\t// watch for extra shuffles caused by a shuffle in a downstream link\n\t\tif ( this.shuffling ) return;\n\n\t\t// let the real model handle firing off shuffles\n\t\tif ( !this.target.shuffling ) {\n\t\t\tthis.target.shuffle( newIndices );\n\t\t} else {\n\t\t\tshuffle( this, newIndices, true );\n\t\t}\n\n\t}\n\n\tsource () {\n\t\tif ( this.target.source ) return this.target.source();\n\t\telse return this.target;\n\t}\n\n\tteardown () {\n\t\tif ( this._link ) this._link.teardown();\n\t\tthis.target.unregisterLink( this );\n\t\tthis.children.forEach( teardown );\n\t}\n}\n\nModelBase.prototype.link = function link ( model, keypath, options ) {\n\tconst lnk = this._link || new LinkModel( this.parent, this, model, this.key );\n\tlnk.implicit = options && options.implicit;\n\tlnk.mapping = options && options.mapping;\n\tlnk.sourcePath = keypath;\n\tlnk.rootLink = true;\n\tif ( this._link ) this._link.relinking( model, false );\n\tthis.rebind( lnk, this, false );\n\tfireShuffleTasks();\n\n\tthis._link = lnk;\n\tlnk.markedAll();\n\n\tthis.notifyUpstream();\n\treturn lnk;\n};\n\nModelBase.prototype.unlink = function unlink () {\n\tif ( this._link ) {\n\t\tconst ln = this._link;\n\t\tthis._link = undefined;\n\t\tln.rebind( this, ln, false );\n\t\tfireShuffleTasks();\n\t\tln.teardown();\n\t\tthis.notifyUpstream();\n\t}\n};\n","import { removeFromArray } from 'utils/array';\nimport { isFunction } from 'utils/is';\n\nexport default class TransitionManager {\n\tconstructor ( callback, parent ) {\n\t\tthis.callback = callback;\n\t\tthis.parent = parent;\n\n\t\tthis.intros = [];\n\t\tthis.outros = [];\n\n\t\tthis.children = [];\n\t\tthis.totalChildren = this.outroChildren = 0;\n\n\t\tthis.detachQueue = [];\n\t\tthis.outrosComplete = false;\n\n\t\tif ( parent ) {\n\t\t\tparent.addChild( this );\n\t\t}\n\t}\n\n\tadd ( transition ) {\n\t\tconst list = transition.isIntro ? this.intros : this.outros;\n\t\ttransition.starting = true;\n\t\tlist.push( transition );\n\t}\n\n\taddChild ( child ) {\n\t\tthis.children.push( child );\n\n\t\tthis.totalChildren += 1;\n\t\tthis.outroChildren += 1;\n\t}\n\n\tdecrementOutros () {\n\t\tthis.outroChildren -= 1;\n\t\tcheck( this );\n\t}\n\n\tdecrementTotal () {\n\t\tthis.totalChildren -= 1;\n\t\tcheck( this );\n\t}\n\n\tdetachNodes () {\n\t\tthis.detachQueue.forEach( detach );\n\t\tthis.children.forEach( _detachNodes );\n\t\tthis.detachQueue = [];\n\t}\n\n\tready () {\n\t\tif ( this.detachQueue.length ) detachImmediate( this );\n\t}\n\n\tremove ( transition ) {\n\t\tconst list = transition.isIntro ? this.intros : this.outros;\n\t\tremoveFromArray( list, transition );\n\t\tcheck( this );\n\t}\n\n\tstart () {\n\t\tthis.children.forEach( c => c.start() );\n\t\tthis.intros.concat( this.outros ).forEach( t => t.start() );\n\t\tthis.ready = true;\n\t\tcheck( this );\n\t}\n}\n\nfunction detach ( element ) {\n\telement.detach();\n}\n\nfunction _detachNodes ( tm ) { // _ to avoid transpiler quirk\n\ttm.detachNodes();\n}\n\nfunction check ( tm ) {\n\tif ( !tm.ready || tm.outros.length || tm.outroChildren ) return;\n\n\t// If all outros are complete, and we haven't already done this,\n\t// we notify the parent if there is one, otherwise\n\t// start detaching nodes\n\tif ( !tm.outrosComplete ) {\n\t\ttm.outrosComplete = true;\n\n\t\tif ( tm.parent && !tm.parent.outrosComplete ) {\n\t\t\ttm.parent.decrementOutros( tm );\n\t\t} else {\n\t\t\ttm.detachNodes();\n\t\t}\n\t}\n\n\t// Once everything is done, we can notify parent transition\n\t// manager and call the callback\n\tif ( !tm.intros.length && !tm.totalChildren ) {\n\t\tif ( isFunction( tm.callback ) ) {\n\t\t\ttm.callback();\n\t\t}\n\n\t\tif ( tm.parent && !tm.notifiedTotal ) {\n\t\t\ttm.notifiedTotal = true;\n\t\t\ttm.parent.decrementTotal();\n\t\t}\n\t}\n}\n\n// check through the detach queue to see if a node is up or downstream from a\n// transition and if not, go ahead and detach it\nfunction detachImmediate ( manager ) {\n\tconst queue = manager.detachQueue;\n\tconst outros = collectAllOutros( manager );\n\n\tlet i = queue.length;\n\tlet j = 0;\n\tlet node, trans;\n\tstart: while ( i-- ) {\n\t\tnode = queue[i].node;\n\t\tj = outros.length;\n\t\twhile ( j-- ) {\n\t\t\ttrans = outros[j].element.node;\n\t\t\t// check to see if the node is, contains, or is contained by the transitioning node\n\t\t\tif ( trans === node || trans.contains( node ) || node.contains( trans ) ) continue start;\n\t\t}\n\n\t\t// no match, we can drop it\n\t\tqueue[i].detach();\n\t\tqueue.splice( i, 1 );\n\t}\n}\n\nfunction collectAllOutros ( manager, _list ) {\n\tlet list = _list;\n\n\t// if there's no list, we're starting at the root to build one\n\tif ( !list ) {\n\t\tlist = [];\n\t\tlet parent = manager;\n\t\twhile ( parent.parent ) parent = parent.parent;\n\t\treturn collectAllOutros( parent, list );\n\t} else {\n\t\t// grab all outros from child managers\n\t\tlet i = manager.children.length;\n\t\twhile ( i-- ) {\n\t\t\tlist = collectAllOutros( manager.children[i], list );\n\t\t}\n\n\t\t// grab any from this manager if there are any\n\t\tif ( manager.outros.length ) list = list.concat( manager.outros );\n\n\t\treturn list;\n\t}\n}\n","import { addToArray } from 'utils/array';\nimport TransitionManager from './TransitionManager';\n\nlet batch;\n\nconst runloop = {\n\tstart () {\n\t\tlet fulfilPromise;\n\t\tconst promise = new Promise( f => ( fulfilPromise = f ) );\n\n\t\tbatch = {\n\t\t\tpreviousBatch: batch,\n\t\t\ttransitionManager: new TransitionManager( fulfilPromise, batch && batch.transitionManager ),\n\t\t\tfragments: [],\n\t\t\ttasks: [],\n\t\t\timmediateObservers: [],\n\t\t\tdeferredObservers: [],\n\t\t\tpromise\n\t\t};\n\n\t\treturn promise;\n\t},\n\n\tend () {\n\t\tflushChanges();\n\n\t\tif ( !batch.previousBatch ) batch.transitionManager.start();\n\n\t\tbatch = batch.previousBatch;\n\t},\n\n\taddFragment ( fragment ) {\n\t\taddToArray( batch.fragments, fragment );\n\t},\n\n\t// TODO: come up with a better way to handle fragments that trigger their own update\n\taddFragmentToRoot ( fragment ) {\n\t\tif ( !batch ) return;\n\n\t\tlet b = batch;\n\t\twhile ( b.previousBatch ) {\n\t\t\tb = b.previousBatch;\n\t\t}\n\n\t\taddToArray( b.fragments, fragment );\n\t},\n\n\taddObserver ( observer, defer ) {\n\t\tif ( !batch ) {\n\t\t\tobserver.dispatch();\n\t\t} else {\n\t\t\taddToArray( defer ? batch.deferredObservers : batch.immediateObservers, observer );\n\t\t}\n\t},\n\n\tregisterTransition ( transition ) {\n\t\ttransition._manager = batch.transitionManager;\n\t\tbatch.transitionManager.add( transition );\n\t},\n\n\t// synchronise node detachments with transition ends\n\tdetachWhenReady ( thing ) {\n\t\tbatch.transitionManager.detachQueue.push( thing );\n\t},\n\n\tscheduleTask ( task, postRender ) {\n\t\tlet _batch;\n\n\t\tif ( !batch ) {\n\t\t\ttask();\n\t\t} else {\n\t\t\t_batch = batch;\n\t\t\twhile ( postRender && _batch.previousBatch ) {\n\t\t\t\t// this can't happen until the DOM has been fully updated\n\t\t\t\t// otherwise in some situations (with components inside elements)\n\t\t\t\t// transitions and decorators will initialise prematurely\n\t\t\t\t_batch = _batch.previousBatch;\n\t\t\t}\n\n\t\t\t_batch.tasks.push( task );\n\t\t}\n\t},\n\n\tpromise () {\n\t\tif ( !batch ) return Promise.resolve();\n\n\t\tlet target = batch;\n\t\twhile ( target.previousBatch ) {\n\t\t\ttarget = target.previousBatch;\n\t\t}\n\n\t\treturn target.promise || Promise.resolve();\n\t}\n};\n\nexport default runloop;\n\nfunction dispatch ( observer ) {\n\tobserver.dispatch();\n}\n\nfunction flushChanges () {\n\tlet which = batch.immediateObservers;\n\tbatch.immediateObservers = [];\n\twhich.forEach( dispatch );\n\n\t// Now that changes have been fully propagated, we can update the DOM\n\t// and complete other tasks\n\tlet i = batch.fragments.length;\n\tlet fragment;\n\n\twhich = batch.fragments;\n\tbatch.fragments = [];\n\n\twhile ( i-- ) {\n\t\tfragment = which[i];\n\t\tfragment.update();\n\t}\n\n\tbatch.transitionManager.ready();\n\n\twhich = batch.deferredObservers;\n\tbatch.deferredObservers = [];\n\twhich.forEach( dispatch );\n\n\tconst tasks = batch.tasks;\n\tbatch.tasks = [];\n\n\tfor ( i = 0; i < tasks.length; i += 1 ) {\n\t\ttasks[i]();\n\t}\n\n\t// If updating the view caused some model blowback - e.g. a triple\n\t// containing