diff --git a/website/amd/mobiledoc-kit.js b/website/amd/mobiledoc-kit.js index ff1bd1d3b..12e276754 100644 --- a/website/amd/mobiledoc-kit.js +++ b/website/amd/mobiledoc-kit.js @@ -1,47 +1,54 @@ -define('mobiledoc-html-renderer/cards/image', ['exports', 'mobiledoc-html-renderer/utils/render-type'], function (exports, _mobiledocHtmlRendererUtilsRenderType) { +define('mobiledoc-dom-renderer/cards/image', ['exports', 'mobiledoc-dom-renderer/utils/render-type'], function (exports, _mobiledocDomRendererUtilsRenderType) { 'use strict'; exports['default'] = { - name: 'image-card', - type: _mobiledocHtmlRendererUtilsRenderType['default'], + name: 'image', + type: _mobiledocDomRendererUtilsRenderType['default'], render: function render(_ref) { - var env = _ref.env; - var options = _ref.options; var payload = _ref.payload; + var dom = _ref.env.dom; - if (payload.src) { - return ''; - } + var img = dom.createElement('img'); + img.src = payload.src; + return img; } }; }); -define('mobiledoc-html-renderer', ['exports', 'mobiledoc-html-renderer/renderer-factory', 'mobiledoc-html-renderer/utils/render-type'], function (exports, _mobiledocHtmlRendererRendererFactory, _mobiledocHtmlRendererUtilsRenderType) { +define('mobiledoc-dom-renderer', ['exports', 'mobiledoc-dom-renderer/renderer-factory', 'mobiledoc-dom-renderer/utils/render-type'], function (exports, _mobiledocDomRendererRendererFactory, _mobiledocDomRendererUtilsRenderType) { 'use strict'; exports.registerGlobal = registerGlobal; + exports.RENDER_TYPE = _mobiledocDomRendererUtilsRenderType['default']; function registerGlobal(window) { - window.MobiledocHTMLRenderer = _mobiledocHtmlRendererRendererFactory['default']; + window.MobiledocDOMRenderer = _mobiledocDomRendererRendererFactory['default']; } - exports.RENDER_TYPE = _mobiledocHtmlRendererUtilsRenderType['default']; - exports['default'] = _mobiledocHtmlRendererRendererFactory['default']; + exports['default'] = _mobiledocDomRendererRendererFactory['default']; }); -define('mobiledoc-html-renderer/renderer-factory', ['exports', 'mobiledoc-html-renderer/renderers/0-2', 'mobiledoc-html-renderer/renderers/0-3', 'mobiledoc-html-renderer/utils/render-type'], function (exports, _mobiledocHtmlRendererRenderers02, _mobiledocHtmlRendererRenderers03, _mobiledocHtmlRendererUtilsRenderType) { +define('mobiledoc-dom-renderer/renderer-factory', ['exports', 'mobiledoc-dom-renderer/renderers/0-2', 'mobiledoc-dom-renderer/renderers/0-3', 'mobiledoc-dom-renderer/utils/render-type'], function (exports, _mobiledocDomRendererRenderers02, _mobiledocDomRendererRenderers03, _mobiledocDomRendererUtilsRenderType) { 'use strict'; var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })(); function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } } + /** + * runtime DOM renderer + * renders a mobiledoc to DOM + * + * input: mobiledoc + * output: DOM + */ + function validateCards(cards) { if (!Array.isArray(cards)) { throw new Error('`cards` must be passed as an array'); } for (var i = 0; i < cards.length; i++) { var card = cards[i]; - if (card.type !== _mobiledocHtmlRendererUtilsRenderType['default']) { - throw new Error('Card "' + card.name + '" must be of type "' + _mobiledocHtmlRendererUtilsRenderType['default'] + '", was "' + card.type + '"'); + if (card.type !== _mobiledocDomRendererUtilsRenderType['default']) { + throw new Error('Card "' + card.name + '" must be of type "' + _mobiledocDomRendererUtilsRenderType['default'] + '", was "' + card.type + '"'); } if (!card.render) { throw new Error('Card "' + card.name + '" must define `render`'); @@ -55,8 +62,8 @@ define('mobiledoc-html-renderer/renderer-factory', ['exports', 'mobiledoc-html-r } for (var i = 0; i < atoms.length; i++) { var atom = atoms[i]; - if (atom.type !== _mobiledocHtmlRendererUtilsRenderType['default']) { - throw new Error('Atom "' + atom.name + '" must be type "' + _mobiledocHtmlRendererUtilsRenderType['default'] + '", was "' + atom.type + '"'); + if (atom.type !== _mobiledocDomRendererUtilsRenderType['default']) { + throw new Error('Atom "' + atom.name + '" must be type "' + _mobiledocDomRendererUtilsRenderType['default'] + '", was "' + atom.type + '"'); } if (!atom.render) { throw new Error('Atom "' + atom.name + '" must define `render`'); @@ -68,28 +75,44 @@ define('mobiledoc-html-renderer/renderer-factory', ['exports', 'mobiledoc-html-r function RendererFactory() { var _ref = arguments.length <= 0 || arguments[0] === undefined ? {} : arguments[0]; - var cards = _ref.cards; - var atoms = _ref.atoms; - var cardOptions = _ref.cardOptions; + var _ref$cards = _ref.cards; + var cards = _ref$cards === undefined ? [] : _ref$cards; + var _ref$atoms = _ref.atoms; + var atoms = _ref$atoms === undefined ? [] : _ref$atoms; + var _ref$cardOptions = _ref.cardOptions; + var cardOptions = _ref$cardOptions === undefined ? {} : _ref$cardOptions; var unknownCardHandler = _ref.unknownCardHandler; var unknownAtomHandler = _ref.unknownAtomHandler; - var sectionElementRenderer = _ref.sectionElementRenderer; + var _ref$markupElementRenderer = _ref.markupElementRenderer; + var markupElementRenderer = _ref$markupElementRenderer === undefined ? {} : _ref$markupElementRenderer; + var _ref$sectionElementRenderer = _ref.sectionElementRenderer; + var sectionElementRenderer = _ref$sectionElementRenderer === undefined ? {} : _ref$sectionElementRenderer; + var dom = _ref.dom; + var _ref$markupSanitizer = _ref.markupSanitizer; + var markupSanitizer = _ref$markupSanitizer === undefined ? null : _ref$markupSanitizer; _classCallCheck(this, RendererFactory); - cards = cards || []; validateCards(cards); - atoms = atoms || []; validateAtoms(atoms); - cardOptions = cardOptions || {}; - this.state = { + if (!dom) { + if (typeof window === 'undefined') { + throw new Error('A `dom` option must be provided to the renderer when running without window.document'); + } + dom = window.document; + } + + this.options = { cards: cards, atoms: atoms, cardOptions: cardOptions, unknownCardHandler: unknownCardHandler, unknownAtomHandler: unknownAtomHandler, - sectionElementRenderer: sectionElementRenderer + markupElementRenderer: markupElementRenderer, + sectionElementRenderer: sectionElementRenderer, + dom: dom, + markupSanitizer: markupSanitizer }; } @@ -99,12 +122,13 @@ define('mobiledoc-html-renderer/renderer-factory', ['exports', 'mobiledoc-html-r var version = mobiledoc.version; switch (version) { - case _mobiledocHtmlRendererRenderers02.MOBILEDOC_VERSION: + case _mobiledocDomRendererRenderers02.MOBILEDOC_VERSION: case undefined: case null: - return new _mobiledocHtmlRendererRenderers02['default'](mobiledoc, this.state).render(); - case _mobiledocHtmlRendererRenderers03.MOBILEDOC_VERSION: - return new _mobiledocHtmlRendererRenderers03['default'](mobiledoc, this.state).render(); + return new _mobiledocDomRendererRenderers02['default'](mobiledoc, this.options).render(); + case _mobiledocDomRendererRenderers03.MOBILEDOC_VERSION_0_3_0: + case _mobiledocDomRendererRenderers03.MOBILEDOC_VERSION_0_3_1: + return new _mobiledocDomRendererRenderers03['default'](mobiledoc, this.options).render(); default: throw new Error('Unexpected Mobiledoc version "' + version + '"'); } @@ -116,7 +140,7 @@ define('mobiledoc-html-renderer/renderer-factory', ['exports', 'mobiledoc-html-r exports['default'] = RendererFactory; }); -define('mobiledoc-html-renderer/renderers/0-2', ['exports', 'mobiledoc-html-renderer/utils/dom', 'mobiledoc-html-renderer/cards/image', 'mobiledoc-html-renderer/utils/render-type', 'mobiledoc-html-renderer/utils/section-types', 'mobiledoc-html-renderer/utils/tag-names'], function (exports, _mobiledocHtmlRendererUtilsDom, _mobiledocHtmlRendererCardsImage, _mobiledocHtmlRendererUtilsRenderType, _mobiledocHtmlRendererUtilsSectionTypes, _mobiledocHtmlRendererUtilsTagNames) { +define('mobiledoc-dom-renderer/renderers/0-2', ['exports', 'mobiledoc-dom-renderer/utils/dom', 'mobiledoc-dom-renderer/cards/image', 'mobiledoc-dom-renderer/utils/render-type', 'mobiledoc-dom-renderer/utils/section-types', 'mobiledoc-dom-renderer/utils/tag-names', 'mobiledoc-dom-renderer/utils/sanitization-utils', 'mobiledoc-dom-renderer/utils/render-utils'], function (exports, _mobiledocDomRendererUtilsDom, _mobiledocDomRendererCardsImage, _mobiledocDomRendererUtilsRenderType, _mobiledocDomRendererUtilsSectionTypes, _mobiledocDomRendererUtilsTagNames, _mobiledocDomRendererUtilsSanitizationUtils, _mobiledocDomRendererUtilsRenderUtils) { 'use strict'; var _slicedToArray = (function () { function sliceIterator(arr, i) { var _arr = []; var _n = true; var _d = false; var _e = undefined; try { for (var _i = arr[Symbol.iterator](), _s; !(_n = (_s = _i.next()).done); _n = true) { _arr.push(_s.value); if (i && _arr.length === i) break; } } catch (err) { _d = true; _e = err; } finally { try { if (!_n && _i['return']) _i['return'](); } finally { if (_d) throw _e; } } return _arr; } return function (arr, i) { if (Array.isArray(arr)) { return arr; } else if (Symbol.iterator in Object(arr)) { return sliceIterator(arr, i); } else { throw new TypeError('Invalid attempt to destructure non-iterable instance'); } }; })(); @@ -128,32 +152,7 @@ define('mobiledoc-html-renderer/renderers/0-2', ['exports', 'mobiledoc-html-rend var MOBILEDOC_VERSION = '0.2.0'; exports.MOBILEDOC_VERSION = MOBILEDOC_VERSION; - /** - * runtime HTML renderer - * renders a mobiledoc to HTML - * - * input: mobiledoc - * output: HTML - */ - - function createElementFromMarkerType() { - var _ref = arguments.length <= 0 || arguments[0] === undefined ? ['', []] : arguments[0]; - - var _ref2 = _slicedToArray(_ref, 2); - - var tagName = _ref2[0]; - var attributes = _ref2[1]; - - var element = (0, _mobiledocHtmlRendererUtilsDom.createElement)(tagName); - attributes = attributes || []; - - for (var i = 0, l = attributes.length; i < l; i = i + 2) { - var propName = attributes[i], - propValue = attributes[i + 1]; - (0, _mobiledocHtmlRendererUtilsDom.setAttribute)(element, propName, propValue); - } - return element; - } + var IMAGE_SECTION_TAG_NAME = 'img'; function validateVersion(version) { if (version !== MOBILEDOC_VERSION) { @@ -162,13 +161,17 @@ define('mobiledoc-html-renderer/renderers/0-2', ['exports', 'mobiledoc-html-rend } var Renderer = (function () { - function Renderer(mobiledoc, state) { + function Renderer(mobiledoc, options) { + var _this = this; + _classCallCheck(this, Renderer); - var cards = state.cards; - var cardOptions = state.cardOptions; - var unknownCardHandler = state.unknownCardHandler; - var sectionElementRenderer = state.sectionElementRenderer; + var cards = options.cards; + var cardOptions = options.cardOptions; + var unknownCardHandler = options.unknownCardHandler; + var markupElementRenderer = options.markupElementRenderer; + var sectionElementRenderer = options.sectionElementRenderer; + var dom = options.dom; var version = mobiledoc.version; var sectionData = mobiledoc.sections; @@ -179,39 +182,56 @@ define('mobiledoc-html-renderer/renderers/0-2', ['exports', 'mobiledoc-html-rend var markerTypes = _sectionData[0]; var sections = _sectionData[1]; - this.root = (0, _mobiledocHtmlRendererUtilsDom.createDocumentFragment)(); + this.dom = dom; + this.root = dom.createDocumentFragment(); this.markerTypes = markerTypes; this.sections = sections; this.cards = cards; this.cardOptions = cardOptions; this.unknownCardHandler = unknownCardHandler || this._defaultUnknownCardHandler; - this.sectionElementRenderer = {}; - if (sectionElementRenderer) { - for (var key in sectionElementRenderer) { - if (sectionElementRenderer.hasOwnProperty(key)) { - this.sectionElementRenderer[key.toLowerCase()] = sectionElementRenderer[key]; - } - } - } + this.sectionElementRenderer = { + '__default__': _mobiledocDomRendererUtilsRenderUtils.defaultSectionElementRenderer + }; + Object.keys(sectionElementRenderer).forEach(function (key) { + _this.sectionElementRenderer[key.toLowerCase()] = sectionElementRenderer[key]; + }); + this.markupElementRenderer = { + '__default__': _mobiledocDomRendererUtilsRenderUtils.defaultMarkupElementRenderer + }; + Object.keys(markupElementRenderer).forEach(function (key) { + _this.markupElementRenderer[key.toLowerCase()] = markupElementRenderer[key]; + }); + + this._renderCallbacks = []; this._teardownCallbacks = []; + this._renderedChildNodes = []; } _createClass(Renderer, [{ key: 'render', value: function render() { - var _this = this; + var _this2 = this; this.sections.forEach(function (section) { - var rendered = _this.renderSection(section); + var rendered = _this2.renderSection(section); if (rendered) { - (0, _mobiledocHtmlRendererUtilsDom.appendChild)(_this.root, rendered); + _this2.root.appendChild(rendered); } }); - - return { result: this.root.toString(), teardown: function teardown() { - return _this.teardown(); + for (var i = 0; i < this._renderCallbacks.length; i++) { + this._renderCallbacks[i](); + } + // maintain a reference to child nodes so they can be cleaned up later by teardown + this._renderedChildNodes = []; + var node = this.root.firstChild; + while (node) { + this._renderedChildNodes.push(node); + node = node.nextSibling; + } + return { result: this.root, teardown: function teardown() { + return _this2.teardown(); } }; } }, { @@ -220,6 +240,12 @@ define('mobiledoc-html-renderer/renderers/0-2', ['exports', 'mobiledoc-html-rend for (var i = 0; i < this._teardownCallbacks.length; i++) { this._teardownCallbacks[i](); } + for (var i = 0; i < this._renderedChildNodes.length; i++) { + var node = this._renderedChildNodes[i]; + if (node.parentNode) { + node.parentNode.removeChild(node); + } + } } }, { key: 'renderSection', @@ -229,55 +255,118 @@ define('mobiledoc-html-renderer/renderers/0-2', ['exports', 'mobiledoc-html-rend var type = _section[0]; switch (type) { - case _mobiledocHtmlRendererUtilsSectionTypes.MARKUP_SECTION_TYPE: + case _mobiledocDomRendererUtilsSectionTypes.MARKUP_SECTION_TYPE: return this.renderMarkupSection(section); - case _mobiledocHtmlRendererUtilsSectionTypes.IMAGE_SECTION_TYPE: + case _mobiledocDomRendererUtilsSectionTypes.IMAGE_SECTION_TYPE: return this.renderImageSection(section); - case _mobiledocHtmlRendererUtilsSectionTypes.LIST_SECTION_TYPE: + case _mobiledocDomRendererUtilsSectionTypes.LIST_SECTION_TYPE: return this.renderListSection(section); - case _mobiledocHtmlRendererUtilsSectionTypes.CARD_SECTION_TYPE: + case _mobiledocDomRendererUtilsSectionTypes.CARD_SECTION_TYPE: return this.renderCardSection(section); default: - throw new Error('Renderer cannot render type "' + type + '"'); + throw new Error('Cannot render mobiledoc section of type "' + type + '"'); } } }, { - key: 'renderListSection', - value: function renderListSection(_ref3) { - var _this2 = this; + key: 'renderMarkersOnElement', + value: function renderMarkersOnElement(element, markers) { + var elements = [element]; + var currentElement = element; - var _ref32 = _slicedToArray(_ref3, 3); + var pushElement = function pushElement(openedElement) { + currentElement.appendChild(openedElement); + elements.push(openedElement); + currentElement = openedElement; + }; - var type = _ref32[0]; - var tagName = _ref32[1]; - var items = _ref32[2]; + for (var i = 0, l = markers.length; i < l; i++) { + var marker = markers[i]; - if (!(0, _mobiledocHtmlRendererUtilsTagNames.isValidSectionTagName)(tagName, _mobiledocHtmlRendererUtilsSectionTypes.LIST_SECTION_TYPE)) { - return; + var _marker = _slicedToArray(marker, 3); + + var openTypes = _marker[0]; + var closeCount = _marker[1]; + var text = _marker[2]; + + for (var j = 0, m = openTypes.length; j < m; j++) { + var markerType = this.markerTypes[openTypes[j]]; + + var _markerType = _slicedToArray(markerType, 2); + + var tagName = _markerType[0]; + var _markerType$1 = _markerType[1]; + var attrs = _markerType$1 === undefined ? [] : _markerType$1; + + if ((0, _mobiledocDomRendererUtilsTagNames.isValidMarkerType)(tagName)) { + pushElement(this.renderMarkupElement(tagName, attrs)); + } else { + closeCount--; + } + } + + currentElement.appendChild((0, _mobiledocDomRendererUtilsDom.createTextNode)(this.dom, text)); + + for (var j = 0, m = closeCount; j < m; j++) { + elements.pop(); + currentElement = elements[elements.length - 1]; + } } - var element = (0, _mobiledocHtmlRendererUtilsDom.createElement)(tagName); - items.forEach(function (li) { - (0, _mobiledocHtmlRendererUtilsDom.appendChild)(element, _this2.renderListItem(li)); - }); - return element; + } + + /** + * @param attrs Array + */ + }, { + key: 'renderMarkupElement', + value: function renderMarkupElement(tagName, attrs) { + tagName = tagName.toLowerCase(); + attrs = (0, _mobiledocDomRendererUtilsSanitizationUtils.reduceAttributes)(attrs); + + var renderer = this.markupElementRendererFor(tagName); + return renderer(tagName, this.dom, attrs); + } + }, { + key: 'markupElementRendererFor', + value: function markupElementRendererFor(tagName) { + return this.markupElementRenderer[tagName] || this.markupElementRenderer.__default__; } }, { key: 'renderListItem', value: function renderListItem(markers) { - var element = (0, _mobiledocHtmlRendererUtilsDom.createElement)('li'); - this._renderMarkersOnElement(element, markers); + var element = this.dom.createElement('li'); + this.renderMarkersOnElement(element, markers); + return element; + } + }, { + key: 'renderListSection', + value: function renderListSection(_ref) { + var _this3 = this; + + var _ref2 = _slicedToArray(_ref, 3); + + var type = _ref2[0]; + var tagName = _ref2[1]; + var listItems = _ref2[2]; + + if (!(0, _mobiledocDomRendererUtilsTagNames.isValidSectionTagName)(tagName, _mobiledocDomRendererUtilsSectionTypes.LIST_SECTION_TYPE)) { + return; + } + var element = this.dom.createElement(tagName); + listItems.forEach(function (li) { + element.appendChild(_this3.renderListItem(li)); + }); return element; } }, { key: 'renderImageSection', - value: function renderImageSection(_ref4) { - var _ref42 = _slicedToArray(_ref4, 2); + value: function renderImageSection(_ref3) { + var _ref32 = _slicedToArray(_ref3, 2); - var type = _ref42[0]; - var url = _ref42[1]; + var type = _ref32[0]; + var src = _ref32[1]; - var element = (0, _mobiledocHtmlRendererUtilsDom.createElement)('img'); - (0, _mobiledocHtmlRendererUtilsDom.setAttribute)(element, 'src', url); + var element = this.dom.createElement(IMAGE_SECTION_TAG_NAME); + element.src = src; return element; } }, { @@ -288,8 +377,8 @@ define('mobiledoc-html-renderer/renderers/0-2', ['exports', 'mobiledoc-html-rend return this.cards[i]; } } - if (name === _mobiledocHtmlRendererCardsImage['default'].name) { - return _mobiledocHtmlRendererCardsImage['default']; + if (name === _mobiledocDomRendererCardsImage['default'].name) { + return _mobiledocDomRendererCardsImage['default']; } return this._createUnknownCard(name); } @@ -298,50 +387,26 @@ define('mobiledoc-html-renderer/renderers/0-2', ['exports', 'mobiledoc-html-rend value: function _createUnknownCard(name) { return { name: name, - type: _mobiledocHtmlRendererUtilsRenderType['default'], + type: _mobiledocDomRendererUtilsRenderType['default'], render: this.unknownCardHandler }; } - }, { - key: 'renderCardSection', - value: function renderCardSection(_ref5) { - var _ref52 = _slicedToArray(_ref5, 3); - - var type = _ref52[0]; - var name = _ref52[1]; - var payload = _ref52[2]; - - var card = this.findCard(name); - - var cardWrapper = this._createCardElement(); - var cardArg = this._createCardArgument(card, payload); - var rendered = card.render(cardArg); - - this._validateCardRender(rendered, card.name); - - if (rendered) { - (0, _mobiledocHtmlRendererUtilsDom.appendChild)(cardWrapper, rendered); - } - - return cardWrapper; - } - }, { - key: '_registerTeardownCallback', - value: function _registerTeardownCallback(callback) { - this._teardownCallbacks.push(callback); - } }, { key: '_createCardArgument', value: function _createCardArgument(card) { - var _this3 = this; + var _this4 = this; var payload = arguments.length <= 1 || arguments[1] === undefined ? {} : arguments[1]; var env = { name: card.name, isInEditor: false, + dom: this.dom, + didRender: function didRender(callback) { + return _this4._registerRenderCallback(callback); + }, onTeardown: function onTeardown(callback) { - return _this3._registerTeardownCallback(callback); + return _this4._registerTeardownCallback(callback); } }; @@ -349,6 +414,34 @@ define('mobiledoc-html-renderer/renderers/0-2', ['exports', 'mobiledoc-html-rend return { env: env, options: options, payload: payload }; } + }, { + key: '_registerRenderCallback', + value: function _registerRenderCallback(callback) { + this._renderCallbacks.push(callback); + } + }, { + key: '_registerTeardownCallback', + value: function _registerTeardownCallback(callback) { + this._teardownCallbacks.push(callback); + } + }, { + key: 'renderCardSection', + value: function renderCardSection(_ref4) { + var _ref42 = _slicedToArray(_ref4, 3); + + var type = _ref42[0]; + var name = _ref42[1]; + var payload = _ref42[2]; + + var card = this.findCard(name); + + var cardArg = this._createCardArgument(card, payload); + var rendered = card.render(cardArg); + + this._validateCardRender(rendered, card.name); + + return rendered; + } }, { key: '_validateCardRender', value: function _validateCardRender(rendered, cardName) { @@ -356,81 +449,40 @@ define('mobiledoc-html-renderer/renderers/0-2', ['exports', 'mobiledoc-html-rend return; } - if (typeof rendered !== 'string') { - throw new Error('Card "' + cardName + '" must render ' + _mobiledocHtmlRendererUtilsRenderType['default'] + ', but result was ' + typeof rendered + '"'); + if (typeof rendered !== 'object') { + throw new Error('Card "' + cardName + '" must render ' + _mobiledocDomRendererUtilsRenderType['default'] + ', but result was "' + rendered + '"'); } } - }, { - key: '_createCardElement', - value: function _createCardElement() { - return (0, _mobiledocHtmlRendererUtilsDom.createElement)('div'); - } }, { key: 'renderMarkupSection', - value: function renderMarkupSection(_ref6) { - var _ref62 = _slicedToArray(_ref6, 3); + value: function renderMarkupSection(_ref5) { + var _ref52 = _slicedToArray(_ref5, 3); - var type = _ref62[0]; - var tagName = _ref62[1]; - var markers = _ref62[2]; + var type = _ref52[0]; + var tagName = _ref52[1]; + var markers = _ref52[2]; - if (!(0, _mobiledocHtmlRendererUtilsTagNames.isValidSectionTagName)(tagName, _mobiledocHtmlRendererUtilsSectionTypes.MARKUP_SECTION_TYPE)) { + tagName = tagName.toLowerCase(); + if (!(0, _mobiledocDomRendererUtilsTagNames.isValidSectionTagName)(tagName, _mobiledocDomRendererUtilsSectionTypes.MARKUP_SECTION_TYPE)) { return; } - var renderer = _mobiledocHtmlRendererUtilsDom.createElement; - var lowerCaseTagName = tagName.toLowerCase(); - if (this.sectionElementRenderer[lowerCaseTagName]) { - renderer = this.sectionElementRenderer[lowerCaseTagName]; - } - var element = renderer(tagName); - this._renderMarkersOnElement(element, markers); + + var renderer = this.sectionElementRendererFor(tagName); + var element = renderer(tagName, this.dom); + + this.renderMarkersOnElement(element, markers); return element; } }, { - key: '_renderMarkersOnElement', - value: function _renderMarkersOnElement(element, markers) { - var elements = [element]; - var currentElement = element; - - for (var i = 0, l = markers.length; i < l; i++) { - var marker = markers[i]; - - var _marker = _slicedToArray(marker, 3); - - var openTypes = _marker[0]; - var closeCount = _marker[1]; - var text = _marker[2]; - - for (var j = 0, m = openTypes.length; j < m; j++) { - var markerType = this.markerTypes[openTypes[j]]; - - var _markerType = _slicedToArray(markerType, 1); - - var tagName = _markerType[0]; - - if ((0, _mobiledocHtmlRendererUtilsTagNames.isValidMarkerType)(tagName)) { - var openedElement = createElementFromMarkerType(markerType); - (0, _mobiledocHtmlRendererUtilsDom.appendChild)(currentElement, openedElement); - elements.push(openedElement); - currentElement = openedElement; - } else { - closeCount--; - } - } - - (0, _mobiledocHtmlRendererUtilsDom.appendChild)(currentElement, (0, _mobiledocHtmlRendererUtilsDom.createTextNode)(text)); - - for (var j = 0, m = closeCount; j < m; j++) { - elements.pop(); - currentElement = elements[elements.length - 1]; - } - } + key: 'sectionElementRendererFor', + value: function sectionElementRendererFor(tagName) { + return this.sectionElementRenderer[tagName] || this.sectionElementRenderer.__default__; } }, { key: '_defaultUnknownCardHandler', get: function get() { - return function (_ref7) { - var name = _ref7.env.name; + return function (_ref6) { + var name = _ref6.env.name; throw new Error('Card "' + name + '" not found but no unknownCardHandler was registered'); }; @@ -442,7 +494,7 @@ define('mobiledoc-html-renderer/renderers/0-2', ['exports', 'mobiledoc-html-rend exports['default'] = Renderer; }); -define('mobiledoc-html-renderer/renderers/0-3', ['exports', 'mobiledoc-html-renderer/utils/dom', 'mobiledoc-html-renderer/cards/image', 'mobiledoc-html-renderer/utils/render-type', 'mobiledoc-html-renderer/utils/section-types', 'mobiledoc-html-renderer/utils/tag-names', 'mobiledoc-html-renderer/utils/marker-types'], function (exports, _mobiledocHtmlRendererUtilsDom, _mobiledocHtmlRendererCardsImage, _mobiledocHtmlRendererUtilsRenderType, _mobiledocHtmlRendererUtilsSectionTypes, _mobiledocHtmlRendererUtilsTagNames, _mobiledocHtmlRendererUtilsMarkerTypes) { +define('mobiledoc-dom-renderer/renderers/0-3', ['exports', 'mobiledoc-dom-renderer/utils/dom', 'mobiledoc-dom-renderer/cards/image', 'mobiledoc-dom-renderer/utils/render-type', 'mobiledoc-dom-renderer/utils/section-types', 'mobiledoc-dom-renderer/utils/tag-names', 'mobiledoc-dom-renderer/utils/sanitization-utils', 'mobiledoc-dom-renderer/utils/render-utils', 'mobiledoc-dom-renderer/utils/marker-types'], function (exports, _mobiledocDomRendererUtilsDom, _mobiledocDomRendererCardsImage, _mobiledocDomRendererUtilsRenderType, _mobiledocDomRendererUtilsSectionTypes, _mobiledocDomRendererUtilsTagNames, _mobiledocDomRendererUtilsSanitizationUtils, _mobiledocDomRendererUtilsRenderUtils, _mobiledocDomRendererUtilsMarkerTypes) { 'use strict'; var _slicedToArray = (function () { function sliceIterator(arr, i) { var _arr = []; var _n = true; var _d = false; var _e = undefined; try { for (var _i = arr[Symbol.iterator](), _s; !(_n = (_s = _i.next()).done); _n = true) { _arr.push(_s.value); if (i && _arr.length === i) break; } } catch (err) { _d = true; _e = err; } finally { try { if (!_n && _i['return']) _i['return'](); } finally { if (_d) throw _e; } } return _arr; } return function (arr, i) { if (Array.isArray(arr)) { return arr; } else if (Symbol.iterator in Object(arr)) { return sliceIterator(arr, i); } else { throw new TypeError('Invalid attempt to destructure non-iterable instance'); } }; })(); @@ -451,44 +503,29 @@ define('mobiledoc-html-renderer/renderers/0-3', ['exports', 'mobiledoc-html-rend function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } } - var MOBILEDOC_VERSION = '0.3.0'; + var MOBILEDOC_VERSION_0_3_0 = '0.3.0'; + exports.MOBILEDOC_VERSION_0_3_0 = MOBILEDOC_VERSION_0_3_0; + var MOBILEDOC_VERSION_0_3_1 = '0.3.1'; + exports.MOBILEDOC_VERSION_0_3_1 = MOBILEDOC_VERSION_0_3_1; + var MOBILEDOC_VERSION = MOBILEDOC_VERSION_0_3_0; exports.MOBILEDOC_VERSION = MOBILEDOC_VERSION; - /** - * runtime HTML renderer - * renders a mobiledoc to HTML - * - * input: mobiledoc - * output: HTML - */ - - function createElementFromMarkerType() { - var _ref = arguments.length <= 0 || arguments[0] === undefined ? ['', []] : arguments[0]; - - var _ref2 = _slicedToArray(_ref, 2); - - var tagName = _ref2[0]; - var attributes = _ref2[1]; - - var element = (0, _mobiledocHtmlRendererUtilsDom.createElement)(tagName); - attributes = attributes || []; - - for (var i = 0, l = attributes.length; i < l; i = i + 2) { - var propName = attributes[i], - propValue = attributes[i + 1]; - (0, _mobiledocHtmlRendererUtilsDom.setAttribute)(element, propName, propValue); - } - return element; - } + var IMAGE_SECTION_TAG_NAME = 'img'; function validateVersion(version) { - if (version !== MOBILEDOC_VERSION) { - throw new Error('Unexpected Mobiledoc version "' + version + '"'); + switch (version) { + case MOBILEDOC_VERSION_0_3_0: + case MOBILEDOC_VERSION_0_3_1: + return; + default: + throw new Error('Unexpected Mobiledoc version "' + version + '"'); } } var Renderer = (function () { function Renderer(mobiledoc, state) { + var _this = this; + _classCallCheck(this, Renderer); var cards = state.cards; @@ -496,7 +533,9 @@ define('mobiledoc-html-renderer/renderers/0-3', ['exports', 'mobiledoc-html-rend var atoms = state.atoms; var unknownCardHandler = state.unknownCardHandler; var unknownAtomHandler = state.unknownAtomHandler; + var markupElementRenderer = state.markupElementRenderer; var sectionElementRenderer = state.sectionElementRenderer; + var dom = state.dom; var version = mobiledoc.version; var sections = mobiledoc.sections; var atomTypes = mobiledoc.atoms; @@ -505,7 +544,8 @@ define('mobiledoc-html-renderer/renderers/0-3', ['exports', 'mobiledoc-html-rend validateVersion(version); - this.root = (0, _mobiledocHtmlRendererUtilsDom.createDocumentFragment)(); + this.dom = dom; + this.root = this.dom.createDocumentFragment(); this.sections = sections; this.atomTypes = atomTypes; this.cardTypes = cardTypes; @@ -516,32 +556,42 @@ define('mobiledoc-html-renderer/renderers/0-3', ['exports', 'mobiledoc-html-rend this.unknownCardHandler = unknownCardHandler || this._defaultUnknownCardHandler; this.unknownAtomHandler = unknownAtomHandler || this._defaultUnknownAtomHandler; - this.sectionElementRenderer = {}; - if (sectionElementRenderer) { - for (var key in sectionElementRenderer) { - if (sectionElementRenderer.hasOwnProperty(key)) { - this.sectionElementRenderer[key.toLowerCase()] = sectionElementRenderer[key]; - } - } - } + this.sectionElementRenderer = { + '__default__': _mobiledocDomRendererUtilsRenderUtils.defaultSectionElementRenderer + }; + Object.keys(sectionElementRenderer).forEach(function (key) { + _this.sectionElementRenderer[key.toLowerCase()] = sectionElementRenderer[key]; + }); + + this.markupElementRenderer = { + '__default__': _mobiledocDomRendererUtilsRenderUtils.defaultMarkupElementRenderer + }; + Object.keys(markupElementRenderer).forEach(function (key) { + _this.markupElementRenderer[key.toLowerCase()] = markupElementRenderer[key]; + }); + this._renderCallbacks = []; this._teardownCallbacks = []; } _createClass(Renderer, [{ key: 'render', value: function render() { - var _this = this; + var _this2 = this; this.sections.forEach(function (section) { - var rendered = _this.renderSection(section); + var rendered = _this2.renderSection(section); if (rendered) { - (0, _mobiledocHtmlRendererUtilsDom.appendChild)(_this.root, rendered); + _this2.root.appendChild(rendered); } }); - - return { result: this.root.toString(), teardown: function teardown() { - return _this.teardown(); + for (var i = 0; i < this._renderCallbacks.length; i++) { + this._renderCallbacks[i](); + } + // maintain a reference to child nodes so they can be cleaned up later by teardown + this._renderedChildNodes = Array.prototype.slice.call(this.root.childNodes); + return { result: this.root, teardown: function teardown() { + return _this2.teardown(); } }; } }, { @@ -550,6 +600,12 @@ define('mobiledoc-html-renderer/renderers/0-3', ['exports', 'mobiledoc-html-rend for (var i = 0; i < this._teardownCallbacks.length; i++) { this._teardownCallbacks[i](); } + for (var i = 0; i < this._renderedChildNodes.length; i++) { + var node = this._renderedChildNodes[i]; + if (node.parentNode) { + node.parentNode.removeChild(node); + } + } } }, { key: 'renderSection', @@ -559,55 +615,128 @@ define('mobiledoc-html-renderer/renderers/0-3', ['exports', 'mobiledoc-html-rend var type = _section[0]; switch (type) { - case _mobiledocHtmlRendererUtilsSectionTypes.MARKUP_SECTION_TYPE: + case _mobiledocDomRendererUtilsSectionTypes.MARKUP_SECTION_TYPE: return this.renderMarkupSection(section); - case _mobiledocHtmlRendererUtilsSectionTypes.IMAGE_SECTION_TYPE: + case _mobiledocDomRendererUtilsSectionTypes.IMAGE_SECTION_TYPE: return this.renderImageSection(section); - case _mobiledocHtmlRendererUtilsSectionTypes.LIST_SECTION_TYPE: + case _mobiledocDomRendererUtilsSectionTypes.LIST_SECTION_TYPE: return this.renderListSection(section); - case _mobiledocHtmlRendererUtilsSectionTypes.CARD_SECTION_TYPE: + case _mobiledocDomRendererUtilsSectionTypes.CARD_SECTION_TYPE: return this.renderCardSection(section); default: - throw new Error('Renderer cannot render type "' + type + '"'); + throw new Error('Cannot render mobiledoc section of type "' + type + '"'); } } }, { - key: 'renderListSection', - value: function renderListSection(_ref3) { - var _this2 = this; + key: 'renderMarkersOnElement', + value: function renderMarkersOnElement(element, markers) { + var elements = [element]; + var currentElement = element; - var _ref32 = _slicedToArray(_ref3, 3); + var pushElement = function pushElement(openedElement) { + currentElement.appendChild(openedElement); + elements.push(openedElement); + currentElement = openedElement; + }; - var type = _ref32[0]; - var tagName = _ref32[1]; - var items = _ref32[2]; + for (var i = 0, l = markers.length; i < l; i++) { + var marker = markers[i]; - if (!(0, _mobiledocHtmlRendererUtilsTagNames.isValidSectionTagName)(tagName, _mobiledocHtmlRendererUtilsSectionTypes.LIST_SECTION_TYPE)) { - return; - } - var element = (0, _mobiledocHtmlRendererUtilsDom.createElement)(tagName); - items.forEach(function (li) { - (0, _mobiledocHtmlRendererUtilsDom.appendChild)(element, _this2.renderListItem(li)); - }); - return element; - } - }, { - key: 'renderListItem', - value: function renderListItem(markers) { - var element = (0, _mobiledocHtmlRendererUtilsDom.createElement)('li'); - this._renderMarkersOnElement(element, markers); + var _marker = _slicedToArray(marker, 4); + + var type = _marker[0]; + var openTypes = _marker[1]; + var closeCount = _marker[2]; + var value = _marker[3]; + + for (var j = 0, m = openTypes.length; j < m; j++) { + var markerType = this.markerTypes[openTypes[j]]; + + var _markerType = _slicedToArray(markerType, 2); + + var tagName = _markerType[0]; + var _markerType$1 = _markerType[1]; + var attrs = _markerType$1 === undefined ? [] : _markerType$1; + + if ((0, _mobiledocDomRendererUtilsTagNames.isValidMarkerType)(tagName)) { + pushElement(this.renderMarkupElement(tagName, attrs)); + } else { + closeCount--; + } + } + + switch (type) { + case _mobiledocDomRendererUtilsMarkerTypes.MARKUP_MARKER_TYPE: + currentElement.appendChild((0, _mobiledocDomRendererUtilsDom.createTextNode)(this.dom, value)); + break; + case _mobiledocDomRendererUtilsMarkerTypes.ATOM_MARKER_TYPE: + currentElement.appendChild(this._renderAtom(value)); + break; + default: + throw new Error('Unknown markup type (' + type + ')'); + } + + for (var j = 0, m = closeCount; j < m; j++) { + elements.pop(); + currentElement = elements[elements.length - 1]; + } + } + } + + /** + * @param attrs Array + */ + }, { + key: 'renderMarkupElement', + value: function renderMarkupElement(tagName, attrs) { + tagName = tagName.toLowerCase(); + attrs = (0, _mobiledocDomRendererUtilsSanitizationUtils.reduceAttributes)(attrs); + + var renderer = this.markupElementRendererFor(tagName); + return renderer(tagName, this.dom, attrs); + } + }, { + key: 'markupElementRendererFor', + value: function markupElementRendererFor(tagName) { + return this.markupElementRenderer[tagName] || this.markupElementRenderer.__default__; + } + }, { + key: 'renderListItem', + value: function renderListItem(markers) { + var element = this.dom.createElement('li'); + this.renderMarkersOnElement(element, markers); + return element; + } + }, { + key: 'renderListSection', + value: function renderListSection(_ref) { + var _this3 = this; + + var _ref2 = _slicedToArray(_ref, 3); + + var type = _ref2[0]; + var tagName = _ref2[1]; + var listItems = _ref2[2]; + + if (!(0, _mobiledocDomRendererUtilsTagNames.isValidSectionTagName)(tagName, _mobiledocDomRendererUtilsSectionTypes.LIST_SECTION_TYPE)) { + return; + } + var element = this.dom.createElement(tagName); + listItems.forEach(function (li) { + element.appendChild(_this3.renderListItem(li)); + }); return element; } }, { key: 'renderImageSection', - value: function renderImageSection(_ref4) { - var _ref42 = _slicedToArray(_ref4, 2); + value: function renderImageSection(_ref3) { + var _ref32 = _slicedToArray(_ref3, 2); - var type = _ref42[0]; - var url = _ref42[1]; + var type = _ref32[0]; + var src = _ref32[1]; - var element = (0, _mobiledocHtmlRendererUtilsDom.createElement)('img'); - (0, _mobiledocHtmlRendererUtilsDom.setAttribute)(element, 'src', url); + var element = this.dom.createElement(IMAGE_SECTION_TAG_NAME); + element.src = src; return element; } }, { @@ -618,8 +747,8 @@ define('mobiledoc-html-renderer/renderers/0-3', ['exports', 'mobiledoc-html-rend return this.cards[i]; } } - if (name === _mobiledocHtmlRendererCardsImage['default'].name) { - return _mobiledocHtmlRendererCardsImage['default']; + if (name === _mobiledocDomRendererCardsImage['default'].name) { + return _mobiledocDomRendererCardsImage['default']; } return this._createUnknownCard(name); } @@ -648,52 +777,26 @@ define('mobiledoc-html-renderer/renderers/0-3', ['exports', 'mobiledoc-html-rend value: function _createUnknownCard(name) { return { name: name, - type: _mobiledocHtmlRendererUtilsRenderType['default'], + type: _mobiledocDomRendererUtilsRenderType['default'], render: this.unknownCardHandler }; } - }, { - key: 'renderCardSection', - value: function renderCardSection(_ref5) { - var _ref52 = _slicedToArray(_ref5, 2); - - var type = _ref52[0]; - var index = _ref52[1]; - - var _findCardByIndex2 = this._findCardByIndex(index); - - var card = _findCardByIndex2.card; - var payload = _findCardByIndex2.payload; - - var cardWrapper = this._createCardElement(); - var cardArg = this._createCardArgument(card, payload); - var rendered = card.render(cardArg); - - this._validateCardRender(rendered, card.name); - - if (rendered) { - (0, _mobiledocHtmlRendererUtilsDom.appendChild)(cardWrapper, rendered); - } - - return cardWrapper; - } - }, { - key: '_registerTeardownCallback', - value: function _registerTeardownCallback(callback) { - this._teardownCallbacks.push(callback); - } }, { key: '_createCardArgument', value: function _createCardArgument(card) { - var _this3 = this; + var _this4 = this; var payload = arguments.length <= 1 || arguments[1] === undefined ? {} : arguments[1]; var env = { name: card.name, isInEditor: false, + dom: this.dom, + didRender: function didRender(callback) { + return _this4._registerRenderCallback(callback); + }, onTeardown: function onTeardown(callback) { - return _this3._registerTeardownCallback(callback); + return _this4._registerTeardownCallback(callback); } }; @@ -702,42 +805,45 @@ define('mobiledoc-html-renderer/renderers/0-3', ['exports', 'mobiledoc-html-rend return { env: env, options: options, payload: payload }; } }, { - key: '_validateCardRender', - value: function _validateCardRender(rendered, cardName) { - if (!rendered) { - return; - } - - if (typeof rendered !== 'string') { - throw new Error('Card "' + cardName + '" must render ' + _mobiledocHtmlRendererUtilsRenderType['default'] + ', but result was ' + typeof rendered + '"'); - } + key: '_registerTeardownCallback', + value: function _registerTeardownCallback(callback) { + this._teardownCallbacks.push(callback); } }, { - key: '_createCardElement', - value: function _createCardElement() { - return (0, _mobiledocHtmlRendererUtilsDom.createElement)('div'); + key: '_registerRenderCallback', + value: function _registerRenderCallback(callback) { + this._renderCallbacks.push(callback); } }, { - key: 'renderMarkupSection', - value: function renderMarkupSection(_ref6) { - var _ref62 = _slicedToArray(_ref6, 3); + key: 'renderCardSection', + value: function renderCardSection(_ref4) { + var _ref42 = _slicedToArray(_ref4, 2); - var type = _ref62[0]; - var tagName = _ref62[1]; - var markers = _ref62[2]; + var type = _ref42[0]; + var index = _ref42[1]; + + var _findCardByIndex2 = this._findCardByIndex(index); + + var card = _findCardByIndex2.card; + var payload = _findCardByIndex2.payload; + + var cardArg = this._createCardArgument(card, payload); + var rendered = card.render(cardArg); + + this._validateCardRender(rendered, card.name); - if (!(0, _mobiledocHtmlRendererUtilsTagNames.isValidSectionTagName)(tagName, _mobiledocHtmlRendererUtilsSectionTypes.MARKUP_SECTION_TYPE)) { + return rendered; + } + }, { + key: '_validateCardRender', + value: function _validateCardRender(rendered, cardName) { + if (!rendered) { return; } - var renderer = _mobiledocHtmlRendererUtilsDom.createElement; - var lowerCaseTagName = tagName.toLowerCase(); - if (this.sectionElementRenderer[lowerCaseTagName]) { - renderer = this.sectionElementRenderer[lowerCaseTagName]; - } - var element = renderer(tagName); - this._renderMarkersOnElement(element, markers); - return element; + if (typeof rendered !== 'object') { + throw new Error('Card "' + cardName + '" must render ' + _mobiledocDomRendererUtilsRenderType['default'] + ', but result was "' + rendered + '"'); + } } }, { key: 'findAtom', @@ -754,19 +860,21 @@ define('mobiledoc-html-renderer/renderers/0-3', ['exports', 'mobiledoc-html-rend value: function _createUnknownAtom(name) { return { name: name, - type: _mobiledocHtmlRendererUtilsRenderType['default'], + type: _mobiledocDomRendererUtilsRenderType['default'], render: this.unknownAtomHandler }; } }, { key: '_createAtomArgument', value: function _createAtomArgument(atom, value, payload) { - var _this4 = this; + var _this5 = this; var env = { name: atom.name, + isInEditor: false, + dom: this.dom, onTeardown: function onTeardown(callback) { - return _this4._registerTeardownCallback(callback); + return _this5._registerTeardownCallback(callback); } }; @@ -781,8 +889,8 @@ define('mobiledoc-html-renderer/renderers/0-3', ['exports', 'mobiledoc-html-rend return; } - if (typeof rendered !== 'string') { - throw new Error('Atom "' + atomName + '" must render ' + _mobiledocHtmlRendererUtilsRenderType['default'] + ', but result was ' + typeof rendered + '"'); + if (typeof rendered !== 'object') { + throw new Error('Atom "' + atomName + '" must render ' + _mobiledocDomRendererUtilsRenderType['default'] + ', but result was "' + rendered + '"'); } } }, { @@ -821,63 +929,38 @@ define('mobiledoc-html-renderer/renderers/0-3', ['exports', 'mobiledoc-html-rend this._validateAtomRender(rendered, atom.name); - return rendered || (0, _mobiledocHtmlRendererUtilsDom.createTextNode)(''); + return rendered || (0, _mobiledocDomRendererUtilsDom.createTextNode)(this.dom, ''); } }, { - key: '_renderMarkersOnElement', - value: function _renderMarkersOnElement(element, markers) { - var elements = [element]; - var currentElement = element; - - for (var i = 0, l = markers.length; i < l; i++) { - var marker = markers[i]; - - var _marker = _slicedToArray(marker, 4); - - var type = _marker[0]; - var openTypes = _marker[1]; - var closeCount = _marker[2]; - var value = _marker[3]; - - for (var j = 0, m = openTypes.length; j < m; j++) { - var markerType = this.markerTypes[openTypes[j]]; - - var _markerType = _slicedToArray(markerType, 1); + key: 'renderMarkupSection', + value: function renderMarkupSection(_ref5) { + var _ref52 = _slicedToArray(_ref5, 3); - var tagName = _markerType[0]; + var type = _ref52[0]; + var tagName = _ref52[1]; + var markers = _ref52[2]; - if ((0, _mobiledocHtmlRendererUtilsTagNames.isValidMarkerType)(tagName)) { - var openedElement = createElementFromMarkerType(markerType); - (0, _mobiledocHtmlRendererUtilsDom.appendChild)(currentElement, openedElement); - elements.push(openedElement); - currentElement = openedElement; - } else { - closeCount--; - } - } + tagName = tagName.toLowerCase(); + if (!(0, _mobiledocDomRendererUtilsTagNames.isValidSectionTagName)(tagName, _mobiledocDomRendererUtilsSectionTypes.MARKUP_SECTION_TYPE)) { + return; + } - switch (type) { - case _mobiledocHtmlRendererUtilsMarkerTypes.MARKUP_MARKER_TYPE: - (0, _mobiledocHtmlRendererUtilsDom.appendChild)(currentElement, (0, _mobiledocHtmlRendererUtilsDom.createTextNode)(value)); - break; - case _mobiledocHtmlRendererUtilsMarkerTypes.ATOM_MARKER_TYPE: - (0, _mobiledocHtmlRendererUtilsDom.appendChild)(currentElement, this._renderAtom(value)); - break; - default: - throw new Error('Unknown markup type (' + type + ')'); - } + var renderer = this.sectionElementRendererFor(tagName); + var element = renderer(tagName, this.dom); - for (var j = 0, m = closeCount; j < m; j++) { - elements.pop(); - currentElement = elements[elements.length - 1]; - } - } + this.renderMarkersOnElement(element, markers); + return element; + } + }, { + key: 'sectionElementRendererFor', + value: function sectionElementRendererFor(tagName) { + return this.sectionElementRenderer[tagName] || this.sectionElementRenderer.__default__; } }, { key: '_defaultUnknownCardHandler', get: function get() { - return function (_ref7) { - var name = _ref7.env.name; + return function (_ref6) { + var name = _ref6.env.name; throw new Error('Card "' + name + '" not found but no unknownCardHandler was registered'); }; @@ -885,8 +968,8 @@ define('mobiledoc-html-renderer/renderers/0-3', ['exports', 'mobiledoc-html-rend }, { key: '_defaultUnknownAtomHandler', get: function get() { - return function (_ref8) { - var name = _ref8.env.name; + return function (_ref7) { + var name = _ref7.env.name; throw new Error('Atom "' + name + '" not found but no unknownAtomHandler was registered'); }; @@ -898,116 +981,40 @@ define('mobiledoc-html-renderer/renderers/0-3', ['exports', 'mobiledoc-html-rend exports['default'] = Renderer; }); -define('mobiledoc-html-renderer/utils/dom', ['exports'], function (exports) { - 'use strict'; - - var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })(); - - exports.createElement = createElement; - exports.appendChild = appendChild; - exports.createTextNode = createTextNode; - exports.setAttribute = setAttribute; - exports.createDocumentFragment = createDocumentFragment; - exports.normalizeTagName = normalizeTagName; - - function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } } - - var VOID_TAGS = 'area base br col command embed hr img input keygen link meta param source track wbr'.split(' '); - - var Element = (function () { - function Element(tagName) { - _classCallCheck(this, Element); - - this.tagName = tagName.toLowerCase(); - this.isVoid = VOID_TAGS.indexOf(this.tagName) !== -1; - this.childNodes = []; - this.attributes = []; - } - - _createClass(Element, [{ - key: 'appendChild', - value: function appendChild(element) { - this.childNodes.push(element); - } - }, { - key: 'setAttribute', - value: function setAttribute(propName, propValue) { - this.attributes.push(propName, propValue); - } - }, { - key: 'toString', - value: function toString() { - var html = '<' + this.tagName; - - if (this.attributes.length) { - for (var i = 0; i < this.attributes.length; i = i + 2) { - var propName = this.attributes[i], - propValue = this.attributes[i + 1]; - html += ' ' + propName + '="' + propValue + '"'; - } - } - html += '>'; +define("mobiledoc-dom-renderer/utils/array-utils", ["exports"], function (exports) { + "use strict"; - if (!this.isVoid) { - for (var i = 0; i < this.childNodes.length; i++) { - html += this.childNodes[i].toString(); - } - html += ''; - } + exports.includes = includes; - return html; + function includes(array, detectValue) { + for (var i = 0; i < array.length; i++) { + var value = array[i]; + if (value === detectValue) { + return true; } - }]); - - return Element; - })(); - - function addHTMLSpaces(text) { - return text.replace(/ /g, '  '); - } - - var TextNode = (function () { - function TextNode(value) { - _classCallCheck(this, TextNode); - - this.value = value; } - - _createClass(TextNode, [{ - key: 'toString', - value: function toString() { - return addHTMLSpaces(this.value); - } - }]); - - return TextNode; - })(); - - function createElement(tagName) { - return new Element(tagName); - } - - function appendChild(target, child) { - target.appendChild(child); - } - - function createTextNode(text) { - return new TextNode(text); + return false; } +}); +define('mobiledoc-dom-renderer/utils/dom', ['exports'], function (exports) { + 'use strict'; - function setAttribute(element, propName, propValue) { - element.setAttribute(propName, propValue); + exports.createTextNode = createTextNode; + exports.normalizeTagName = normalizeTagName; + function addHTMLSpaces(text) { + var nbsp = ' '; + return text.replace(/ /g, ' ' + nbsp); } - function createDocumentFragment() { - return createElement('div'); + function createTextNode(dom, text) { + return dom.createTextNode(addHTMLSpaces(text)); } - function normalizeTagName(name) { - return name.toLowerCase(); + function normalizeTagName(tagName) { + return tagName.toLowerCase(); } }); -define("mobiledoc-html-renderer/utils/marker-types", ["exports"], function (exports) { +define("mobiledoc-dom-renderer/utils/marker-types", ["exports"], function (exports) { "use strict"; var MARKUP_MARKER_TYPE = 0; @@ -1015,54 +1022,139 @@ define("mobiledoc-html-renderer/utils/marker-types", ["exports"], function (expo var ATOM_MARKER_TYPE = 1; exports.ATOM_MARKER_TYPE = ATOM_MARKER_TYPE; }); -define('mobiledoc-html-renderer/utils/render-type', ['exports'], function (exports) { +define('mobiledoc-dom-renderer/utils/render-type', ['exports'], function (exports) { 'use strict'; - exports['default'] = 'html'; -}); -define("mobiledoc-html-renderer/utils/section-types", ["exports"], function (exports) { - "use strict"; - - var MARKUP_SECTION_TYPE = 1; - exports.MARKUP_SECTION_TYPE = MARKUP_SECTION_TYPE; - var IMAGE_SECTION_TYPE = 2; - exports.IMAGE_SECTION_TYPE = IMAGE_SECTION_TYPE; - var LIST_SECTION_TYPE = 3; - exports.LIST_SECTION_TYPE = LIST_SECTION_TYPE; - var CARD_SECTION_TYPE = 10; - exports.CARD_SECTION_TYPE = CARD_SECTION_TYPE; + exports['default'] = 'dom'; }); -define('mobiledoc-html-renderer/utils/tag-names', ['exports', 'mobiledoc-html-renderer/utils/section-types', 'mobiledoc-html-renderer/utils/dom'], function (exports, _mobiledocHtmlRendererUtilsSectionTypes, _mobiledocHtmlRendererUtilsDom) { +define('mobiledoc-dom-renderer/utils/render-utils', ['exports', 'mobiledoc-dom-renderer/utils/tag-names', 'mobiledoc-dom-renderer/utils/sanitization-utils'], function (exports, _mobiledocDomRendererUtilsTagNames, _mobiledocDomRendererUtilsSanitizationUtils) { 'use strict'; - exports.isValidSectionTagName = isValidSectionTagName; - exports.isValidMarkerType = isValidMarkerType; + exports.defaultSectionElementRenderer = defaultSectionElementRenderer; + exports.defaultMarkupElementRenderer = defaultMarkupElementRenderer; - var MARKUP_SECTION_TAG_NAMES = ['p', 'h1', 'h2', 'h3', 'blockquote', 'pull-quote'].map(_mobiledocHtmlRendererUtilsDom.normalizeTagName); - - var LIST_SECTION_TAG_NAMES = ['ul', 'ol'].map(_mobiledocHtmlRendererUtilsDom.normalizeTagName); + function defaultSectionElementRenderer(tagName, dom) { + var element = undefined; + if ((0, _mobiledocDomRendererUtilsTagNames.isMarkupSectionElementName)(tagName)) { + element = dom.createElement(tagName); + } else { + element = dom.createElement('div'); + element.setAttribute('class', tagName); + } - var MARKUP_TYPES = ['b', 'i', 'strong', 'em', 'a', 'u', 'sub', 'sup', 's'].map(_mobiledocHtmlRendererUtilsDom.normalizeTagName); + return element; + } - function contains(array, item) { - return array.indexOf(item) !== -1; + function sanitizeAttribute(tagName, attrName, attrValue) { + if (tagName === 'a' && attrName === 'href') { + return (0, _mobiledocDomRendererUtilsSanitizationUtils.sanitizeHref)(attrValue); + } else { + return attrValue; + } + } + + function defaultMarkupElementRenderer(tagName, dom, attrsObj) { + var element = dom.createElement(tagName); + Object.keys(attrsObj).forEach(function (attrName) { + var attrValue = attrsObj[attrName]; + attrValue = sanitizeAttribute(tagName, attrName, attrValue); + element.setAttribute(attrName, attrValue); + }); + return element; + } +}); +define('mobiledoc-dom-renderer/utils/sanitization-utils', ['exports', 'mobiledoc-dom-renderer/utils/array-utils'], function (exports, _mobiledocDomRendererUtilsArrayUtils) { + 'use strict'; + + exports.sanitizeHref = sanitizeHref; + exports.reduceAttributes = reduceAttributes; + + var PROTOCOL_REGEXP = /^([a-z0-9.+-]+:)/i; + + var badProtocols = ['javascript:', // jshint ignore:line + 'vbscript:' // jshint ignore:line + ]; + + function getProtocol(url) { + var matches = url && url.match(PROTOCOL_REGEXP); + var protocol = matches && matches[0] || ':'; + return protocol; + } + + function sanitizeHref(url) { + var protocol = getProtocol(url); + if ((0, _mobiledocDomRendererUtilsArrayUtils.includes)(badProtocols, protocol)) { + return 'unsafe:' + url; + } + return url; + } + + /** + * @param attributes array + * @return obj with normalized attribute names (lowercased) + */ + + function reduceAttributes(attributes) { + var obj = {}; + for (var i = 0; i < attributes.length; i += 2) { + var key = attributes[i]; + var val = attributes[i + 1]; + obj[key.toLowerCase()] = val; + } + return obj; + } +}); +define("mobiledoc-dom-renderer/utils/section-types", ["exports"], function (exports) { + "use strict"; + + var MARKUP_SECTION_TYPE = 1; + exports.MARKUP_SECTION_TYPE = MARKUP_SECTION_TYPE; + var IMAGE_SECTION_TYPE = 2; + exports.IMAGE_SECTION_TYPE = IMAGE_SECTION_TYPE; + var LIST_SECTION_TYPE = 3; + exports.LIST_SECTION_TYPE = LIST_SECTION_TYPE; + var CARD_SECTION_TYPE = 10; + exports.CARD_SECTION_TYPE = CARD_SECTION_TYPE; +}); +define('mobiledoc-dom-renderer/utils/tag-names', ['exports', 'mobiledoc-dom-renderer/utils/section-types', 'mobiledoc-dom-renderer/utils/dom'], function (exports, _mobiledocDomRendererUtilsSectionTypes, _mobiledocDomRendererUtilsDom) { + 'use strict'; + + exports.isValidSectionTagName = isValidSectionTagName; + exports.isMarkupSectionElementName = isMarkupSectionElementName; + exports.isValidMarkerType = isValidMarkerType; + + var MARKUP_SECTION_TAG_NAMES = ['p', 'h1', 'h2', 'h3', 'h4', 'h5', 'h6', 'blockquote', 'pull-quote', 'aside'].map(_mobiledocDomRendererUtilsDom.normalizeTagName); + + var MARKUP_SECTION_ELEMENT_NAMES = ['p', 'h1', 'h2', 'h3', 'h4', 'h5', 'h6', 'blockquote', 'aside'].map(_mobiledocDomRendererUtilsDom.normalizeTagName); + + var LIST_SECTION_TAG_NAMES = ['ul', 'ol'].map(_mobiledocDomRendererUtilsDom.normalizeTagName); + + var MARKUP_TYPES = ['b', 'i', 'strong', 'em', 'a', 'u', 'sub', 'sup', 's', 'code'].map(_mobiledocDomRendererUtilsDom.normalizeTagName); + + function contains(array, item) { + return array.indexOf(item) !== -1; } function isValidSectionTagName(tagName, sectionType) { - tagName = (0, _mobiledocHtmlRendererUtilsDom.normalizeTagName)(tagName); + tagName = (0, _mobiledocDomRendererUtilsDom.normalizeTagName)(tagName); switch (sectionType) { - case _mobiledocHtmlRendererUtilsSectionTypes.MARKUP_SECTION_TYPE: + case _mobiledocDomRendererUtilsSectionTypes.MARKUP_SECTION_TYPE: return contains(MARKUP_SECTION_TAG_NAMES, tagName); - case _mobiledocHtmlRendererUtilsSectionTypes.LIST_SECTION_TYPE: + case _mobiledocDomRendererUtilsSectionTypes.LIST_SECTION_TYPE: return contains(LIST_SECTION_TAG_NAMES, tagName); default: throw new Error('Cannot validate tagName for unknown section type "' + sectionType + '"'); } } + function isMarkupSectionElementName(tagName) { + tagName = (0, _mobiledocDomRendererUtilsDom.normalizeTagName)(tagName); + return contains(MARKUP_SECTION_ELEMENT_NAMES, tagName); + } + function isValidMarkerType(type) { - type = (0, _mobiledocHtmlRendererUtilsDom.normalizeTagName)(type); + type = (0, _mobiledocDomRendererUtilsDom.normalizeTagName)(type); return contains(MARKUP_TYPES, type); } }); @@ -1104,11 +1196,15 @@ define('mobiledoc-kit/editor/edit-history', ['exports', 'mobiledoc-kit/parsers/m } var Snapshot = (function () { - function Snapshot(editor) { + function Snapshot(takenAt, editor) { + var editAction = arguments.length <= 2 || arguments[2] === undefined ? null : arguments[2]; + _classCallCheck(this, Snapshot); this.mobiledoc = editor.serialize(); this.editor = editor; + this.editAction = editAction; + this.takenAt = takenAt; this.snapshotRange(); } @@ -1159,6 +1255,11 @@ define('mobiledoc-kit/editor/edit-history', ['exports', 'mobiledoc-kit/parsers/m return head.toRange(tail); } } + }, { + key: 'groupsWith', + value: function groupsWith(groupingTimeout, editAction, takenAt) { + return editAction !== null && this.editAction === editAction && this.takenAt + groupingTimeout > takenAt; + } }]); return Snapshot; @@ -1167,7 +1268,7 @@ define('mobiledoc-kit/editor/edit-history', ['exports', 'mobiledoc-kit/parsers/m exports.Snapshot = Snapshot; var EditHistory = (function () { - function EditHistory(editor, queueLength) { + function EditHistory(editor, queueLength, groupingTimeout) { _classCallCheck(this, EditHistory); this.editor = editor; @@ -1175,6 +1276,7 @@ define('mobiledoc-kit/editor/edit-history', ['exports', 'mobiledoc-kit/parsers/m this._redoStack = new _mobiledocKitUtilsFixedQueue['default'](queueLength); this._pendingSnapshot = null; + this._groupingTimeout = groupingTimeout; } _createClass(EditHistory, [{ @@ -1188,14 +1290,20 @@ define('mobiledoc-kit/editor/edit-history', ['exports', 'mobiledoc-kit/parsers/m }, { key: 'storeSnapshot', value: function storeSnapshot() { + var editAction = arguments.length <= 0 || arguments[0] === undefined ? null : arguments[0]; + + var now = Date.now(); // store pending snapshot - if (this._pendingSnapshot) { - this._undoStack.push(this._pendingSnapshot); + var pendingSnapshot = this._pendingSnapshot; + if (pendingSnapshot) { + if (!pendingSnapshot.groupsWith(this._groupingTimeout, editAction, now)) { + this._undoStack.push(pendingSnapshot); + } this._redoStack.clear(); } // take new pending snapshot to store next time `storeSnapshot` is called - this._pendingSnapshot = new Snapshot(this.editor); + this._pendingSnapshot = new Snapshot(now, this.editor, editAction); } }, { key: 'stepBackward', @@ -1205,7 +1313,7 @@ define('mobiledoc-kit/editor/edit-history', ['exports', 'mobiledoc-kit/parsers/m var snapshot = this._undoStack.pop(); if (snapshot) { - this._redoStack.push(new Snapshot(this.editor)); + this._redoStack.push(new Snapshot(Date.now(), this.editor)); this._restoreFromSnapshot(snapshot, postEditor); } } @@ -1214,7 +1322,7 @@ define('mobiledoc-kit/editor/edit-history', ['exports', 'mobiledoc-kit/parsers/m value: function stepForward(postEditor) { var snapshot = this._redoStack.pop(); if (snapshot) { - this._undoStack.push(new Snapshot(this.editor)); + this._undoStack.push(new Snapshot(Date.now(), this.editor)); this._restoreFromSnapshot(snapshot, postEditor); } postEditor.cancelSnapshot(); @@ -1409,7 +1517,7 @@ define('mobiledoc-kit/editor/edit-state', ['exports', 'mobiledoc-kit/utils/array exports['default'] = EditState; }); -define('mobiledoc-kit/editor/editor', ['exports', 'mobiledoc-kit/views/tooltip', 'mobiledoc-kit/editor/post', 'mobiledoc-kit/cards/image', 'mobiledoc-kit/utils/key', 'mobiledoc-kit/parsers/mobiledoc', 'mobiledoc-kit/parsers/html', 'mobiledoc-kit/parsers/dom', 'mobiledoc-kit/renderers/editor-dom', 'mobiledoc-kit/models/render-tree', 'mobiledoc-kit/renderers/mobiledoc', 'mobiledoc-kit/utils/merge', 'mobiledoc-kit/utils/dom-utils', 'mobiledoc-kit/utils/array-utils', 'mobiledoc-kit/utils/element-utils', 'mobiledoc-kit/utils/cursor', 'mobiledoc-kit/utils/cursor/range', 'mobiledoc-kit/utils/cursor/position', 'mobiledoc-kit/models/post-node-builder', 'mobiledoc-kit/editor/text-input-handlers', 'mobiledoc-kit/editor/key-commands', 'mobiledoc-kit/models/card', 'mobiledoc-kit/utils/assert', 'mobiledoc-kit/editor/mutation-handler', 'mobiledoc-kit/editor/edit-history', 'mobiledoc-kit/editor/event-manager', 'mobiledoc-kit/editor/edit-state', 'mobiledoc-html-renderer', 'mobiledoc-text-renderer', 'mobiledoc-kit/models/lifecycle-callbacks', 'mobiledoc-kit/utils/log-manager', 'mobiledoc-kit/utils/to-range', 'mobiledoc-kit/utils/mobiledoc-error'], function (exports, _mobiledocKitViewsTooltip, _mobiledocKitEditorPost, _mobiledocKitCardsImage, _mobiledocKitUtilsKey, _mobiledocKitParsersMobiledoc, _mobiledocKitParsersHtml, _mobiledocKitParsersDom, _mobiledocKitRenderersEditorDom, _mobiledocKitModelsRenderTree, _mobiledocKitRenderersMobiledoc, _mobiledocKitUtilsMerge, _mobiledocKitUtilsDomUtils, _mobiledocKitUtilsArrayUtils, _mobiledocKitUtilsElementUtils, _mobiledocKitUtilsCursor, _mobiledocKitUtilsCursorRange, _mobiledocKitUtilsCursorPosition, _mobiledocKitModelsPostNodeBuilder, _mobiledocKitEditorTextInputHandlers, _mobiledocKitEditorKeyCommands, _mobiledocKitModelsCard, _mobiledocKitUtilsAssert, _mobiledocKitEditorMutationHandler, _mobiledocKitEditorEditHistory, _mobiledocKitEditorEventManager, _mobiledocKitEditorEditState, _mobiledocHtmlRenderer, _mobiledocTextRenderer, _mobiledocKitModelsLifecycleCallbacks, _mobiledocKitUtilsLogManager, _mobiledocKitUtilsToRange, _mobiledocKitUtilsMobiledocError) { +define('mobiledoc-kit/editor/editor', ['exports', 'mobiledoc-kit/views/tooltip', 'mobiledoc-kit/editor/post', 'mobiledoc-kit/cards/image', 'mobiledoc-kit/utils/key', 'mobiledoc-kit/parsers/mobiledoc', 'mobiledoc-kit/parsers/html', 'mobiledoc-kit/parsers/dom', 'mobiledoc-kit/renderers/editor-dom', 'mobiledoc-kit/models/render-tree', 'mobiledoc-kit/renderers/mobiledoc', 'mobiledoc-kit/utils/merge', 'mobiledoc-kit/utils/dom-utils', 'mobiledoc-kit/utils/array-utils', 'mobiledoc-kit/utils/element-utils', 'mobiledoc-kit/utils/cursor', 'mobiledoc-kit/utils/cursor/range', 'mobiledoc-kit/utils/cursor/position', 'mobiledoc-kit/utils/environment', 'mobiledoc-kit/models/post-node-builder', 'mobiledoc-kit/editor/text-input-handlers', 'mobiledoc-kit/editor/key-commands', 'mobiledoc-kit/models/card', 'mobiledoc-kit/utils/assert', 'mobiledoc-kit/editor/mutation-handler', 'mobiledoc-kit/editor/edit-history', 'mobiledoc-kit/editor/event-manager', 'mobiledoc-kit/editor/edit-state', 'mobiledoc-dom-renderer', 'mobiledoc-text-renderer', 'mobiledoc-kit/models/lifecycle-callbacks', 'mobiledoc-kit/utils/log-manager', 'mobiledoc-kit/utils/to-range', 'mobiledoc-kit/utils/mobiledoc-error'], function (exports, _mobiledocKitViewsTooltip, _mobiledocKitEditorPost, _mobiledocKitCardsImage, _mobiledocKitUtilsKey, _mobiledocKitParsersMobiledoc, _mobiledocKitParsersHtml, _mobiledocKitParsersDom, _mobiledocKitRenderersEditorDom, _mobiledocKitModelsRenderTree, _mobiledocKitRenderersMobiledoc, _mobiledocKitUtilsMerge, _mobiledocKitUtilsDomUtils, _mobiledocKitUtilsArrayUtils, _mobiledocKitUtilsElementUtils, _mobiledocKitUtilsCursor, _mobiledocKitUtilsCursorRange, _mobiledocKitUtilsCursorPosition, _mobiledocKitUtilsEnvironment, _mobiledocKitModelsPostNodeBuilder, _mobiledocKitEditorTextInputHandlers, _mobiledocKitEditorKeyCommands, _mobiledocKitModelsCard, _mobiledocKitUtilsAssert, _mobiledocKitEditorMutationHandler, _mobiledocKitEditorEditHistory, _mobiledocKitEditorEventManager, _mobiledocKitEditorEditState, _mobiledocDomRenderer, _mobiledocTextRenderer, _mobiledocKitModelsLifecycleCallbacks, _mobiledocKitUtilsLogManager, _mobiledocKitUtilsToRange, _mobiledocKitUtilsMobiledocError) { 'use strict'; var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })(); @@ -1430,6 +1538,7 @@ define('mobiledoc-kit/editor/editor', ['exports', 'mobiledoc-kit/views/tooltip', spellcheck: true, autofocus: true, undoDepth: 5, + undoBlockTimeout: 5000, // ms for an undo event cards: [], atoms: [], cardOptions: {}, @@ -1540,7 +1649,7 @@ define('mobiledoc-kit/editor/editor', ['exports', 'mobiledoc-kit/views/tooltip', this.post = this.loadPost(); this._renderTree = new _mobiledocKitModelsRenderTree['default'](this.post); - this._editHistory = new _mobiledocKitEditorEditHistory['default'](this, this.undoDepth); + this._editHistory = new _mobiledocKitEditorEditHistory['default'](this, this.undoDepth, this.undoBlockTimeout); this._eventManager = new _mobiledocKitEditorEventManager['default'](this); this._mutationHandler = new _mobiledocKitEditorMutationHandler['default'](this); this._editState = new _mobiledocKitEditorEditState['default'](this); @@ -1698,6 +1807,22 @@ define('mobiledoc-kit/editor/editor', ['exports', 'mobiledoc-kit/views/tooltip', this.keyCommands.unshift(keyCommand); } + /** + * @param {String} name If the keyCommand event has a name attribute it can be removed. + * @public + */ + }, { + key: 'unregisterKeyCommands', + value: function unregisterKeyCommands(name) { + for (var i = this.keyCommands.length - 1; i > -1; i--) { + var keyCommand = this.keyCommands[i]; + + if (keyCommand.name === name) { + this.keyCommands.splice(i, 1); + } + } + } + /** * Convenience for {@link PostEditor#deleteAtPosition}. Deletes and puts the * cursor in the new position. @@ -1981,8 +2106,15 @@ define('mobiledoc-kit/editor/editor', ['exports', 'mobiledoc-kit/views/tooltip', switch (format) { case 'html': - rendered = new _mobiledocHtmlRenderer['default'](rendererOptions).render(mobiledoc); - return rendered.result; + var result = undefined; + if (_mobiledocKitUtilsEnvironment['default'].hasDOM()) { + rendered = new _mobiledocDomRenderer['default'](rendererOptions).render(mobiledoc); + result = '
' + (0, _mobiledocKitUtilsDomUtils.serializeHTML)(rendered.result) + '
'; + } else { + // Fallback to text serialization + result = this.serializePost(post, 'text', options); + } + return result; case 'text': rendered = new _mobiledocTextRenderer['default'](rendererOptions).render(mobiledoc); return rendered.result; @@ -2142,7 +2274,7 @@ define('mobiledoc-kit/editor/editor', ['exports', 'mobiledoc-kit/views/tooltip', if (postEditor._shouldCancelSnapshot) { this._editHistory._pendingSnapshot = null; } - this._editHistory.storeSnapshot(); + this._editHistory.storeSnapshot(postEditor.editActionTaken); return result; } @@ -3094,6 +3226,16 @@ define('mobiledoc-kit/editor/key-commands', ['exports', 'mobiledoc-kit/utils/key run: function run(editor) { editor.toggleMarkup('em'); } + }, { + str: 'META+U', + run: function run(editor) { + editor.toggleMarkup('u'); + } + }, { + str: 'CTRL+U', + run: function run(editor) { + editor.toggleMarkup('u'); + } }, { str: 'CTRL+K', run: function run(editor) { @@ -3434,6 +3576,14 @@ define('mobiledoc-kit/editor/post', ['exports', 'mobiledoc-kit/utils/cursor/posi AFTER_COMPLETE: 'afterComplete' }; + // There are only two events that we're concerned about for Undo, that is inserting text and deleting content. + // These are the only two states that go on a "run" and create a combined undo, everything else has it's own + // deadicated undo. + var EDIT_ACTIONS = { + INSERT_TEXT: 1, + DELETE: 2 + }; + /** * The PostEditor is used to modify a post. It should not be instantiated directly. * Instead, a new instance of a PostEditor is created by the editor and passed @@ -3463,6 +3613,7 @@ define('mobiledoc-kit/editor/post', ['exports', 'mobiledoc-kit/utils/cursor/posi this._callbacks = new _mobiledocKitModelsLifecycleCallbacks['default']((0, _mobiledocKitUtilsArrayUtils.values)(CALLBACK_QUEUES)); this._didComplete = false; + this.editActionTaken = null; this._renderRange = function () { return _this.editor.selectRange(_this._range); @@ -3552,6 +3703,8 @@ define('mobiledoc-kit/editor/post', ['exports', 'mobiledoc-kit/utils/cursor/posi value: function deleteRange(range) { (0, _mobiledocKitUtilsAssert['default'])("Must pass MobiledocKit Range to `deleteRange`", range instanceof _mobiledocKitUtilsCursorRange['default']); + this.editActionTaken = EDIT_ACTIONS.DELETE; + var head = range.head; var headSection = range.head.section; var tail = range.tail; @@ -4083,6 +4236,8 @@ define('mobiledoc-kit/editor/post', ['exports', 'mobiledoc-kit/utils/cursor/posi (0, _mobiledocKitUtilsAssert['default'])('Cannot insert markers at non-markerable position', section.isMarkerable); + this.editActionTaken = EDIT_ACTIONS.INSERT_TEXT; + var edit = section.splitMarkerAtOffset(offset); edit.removed.forEach(function (marker) { return _this9._scheduleForRemoval(marker); @@ -5473,7 +5628,7 @@ define('mobiledoc-kit/editor/text-input-handlers', ['exports'], function (export * Does nothing if the cursor position is not at the start of the section. * * @param {Editor} editor - * @param {String} headingTagName ("h1","h2","h3") + * @param {String} headingTagName ('h1', 'h2', 'h3', 'h4', 'h5', 'h6') * @public */ @@ -5512,8 +5667,15 @@ define('mobiledoc-kit/editor/text-input-handlers', ['exports'], function (export } }, { name: 'heading', - // "# " -> h1, "## " -> h2, "### " -> h3 - match: /^(#{1,3}) $/, + /* + * "# " -> h1 + * "## " -> h2 + * "### " -> h3 + * "#### " -> h4 + * "##### " -> h5 + * "###### " -> h6 + */ + match: /^(#{1,6}) $/, run: function run(editor, matches) { var capture = matches[1]; var headingTag = 'h' + capture.length; @@ -7072,15 +7234,15 @@ define('mobiledoc-kit/models/markup-section', ['exports', 'mobiledoc-kit/models/ function _inherits(subClass, superClass) { if (typeof superClass !== 'function' && superClass !== null) { throw new TypeError('Super expression must either be null or a function, not ' + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; } // valid values of `tagName` for a MarkupSection - var VALID_MARKUP_SECTION_TAGNAMES = ['p', 'h3', 'h2', 'h1', 'blockquote', 'pull-quote'].map(_mobiledocKitUtilsDomUtils.normalizeTagName); + var VALID_MARKUP_SECTION_TAGNAMES = ['aside', 'blockquote', 'h1', 'h2', 'h3', 'h4', 'h5', 'h6', 'p'].map(_mobiledocKitUtilsDomUtils.normalizeTagName); exports.VALID_MARKUP_SECTION_TAGNAMES = VALID_MARKUP_SECTION_TAGNAMES; // valid element names for a MarkupSection. A MarkupSection with a tagName // not in this will be rendered as a div with a className matching the // tagName - var MARKUP_SECTION_ELEMENT_NAMES = ['p', 'h3', 'h2', 'h1', 'blockquote'].map(_mobiledocKitUtilsDomUtils.normalizeTagName); + var MARKUP_SECTION_ELEMENT_NAMES = ['aside', 'blockquote', 'h1', 'h2', 'h3', 'h4', 'h5', 'h6', 'p'].map(_mobiledocKitUtilsDomUtils.normalizeTagName); exports.MARKUP_SECTION_ELEMENT_NAMES = MARKUP_SECTION_ELEMENT_NAMES; - var DEFAULT_TAG_NAME = VALID_MARKUP_SECTION_TAGNAMES[0]; + var DEFAULT_TAG_NAME = VALID_MARKUP_SECTION_TAGNAMES[8]; exports.DEFAULT_TAG_NAME = DEFAULT_TAG_NAME; var MarkupSection = (function (_Markerable) { @@ -7124,13 +7286,13 @@ define('mobiledoc-kit/models/markup', ['exports', 'mobiledoc-kit/utils/dom-utils function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } } - var VALID_MARKUP_TAGNAMES = ['b', 'i', 'strong', 'em', 'a', 'u', 'sub', // subscript + var VALID_MARKUP_TAGNAMES = ['a', 'b', 'code', 'em', 'i', 's', // strikethrough + 'strong', 'sub', // subscript 'sup', // superscript - 's' // strikethrough - ].map(_mobiledocKitUtilsDomUtils.normalizeTagName); + 'u'].map(_mobiledocKitUtilsDomUtils.normalizeTagName); exports.VALID_MARKUP_TAGNAMES = VALID_MARKUP_TAGNAMES; - var VALID_ATTRIBUTES = ['href', 'ref']; + var VALID_ATTRIBUTES = ['href', 'rel']; exports.VALID_ATTRIBUTES = VALID_ATTRIBUTES; @@ -8411,9 +8573,275 @@ define('mobiledoc-kit/parsers/mobiledoc/0-2', ['exports', 'mobiledoc-kit/rendere value: function parseMarkupSection(_ref5, post) { var _ref52 = _slicedToArray(_ref5, 3); - var type = _ref52[0]; - var tagName = _ref52[1]; - var markers = _ref52[2]; + var type = _ref52[0]; + var tagName = _ref52[1]; + var markers = _ref52[2]; + + var section = this.builder.createMarkupSection(tagName.toLowerCase() === 'pull-quote' ? 'aside' : tagName); + post.sections.append(section); + this.parseMarkers(markers, section); + // Strip blank markers after they have been created. This ensures any + // markup they include has been correctly populated. + (0, _mobiledocKitUtilsArrayUtils.filter)(section.markers, function (m) { + return m.isBlank; + }).forEach(function (m) { + section.markers.remove(m); + }); + } + }, { + key: 'parseListSection', + value: function parseListSection(_ref6, post) { + var _ref62 = _slicedToArray(_ref6, 3); + + var type = _ref62[0]; + var tagName = _ref62[1]; + var items = _ref62[2]; + + var section = this.builder.createListSection(tagName); + post.sections.append(section); + this.parseListItems(items, section); + } + }, { + key: 'parseListItems', + value: function parseListItems(items, section) { + var _this3 = this; + + items.forEach(function (i) { + return _this3.parseListItem(i, section); + }); + } + }, { + key: 'parseListItem', + value: function parseListItem(markers, section) { + var item = this.builder.createListItem(); + this.parseMarkers(markers, item); + section.items.append(item); + } + }, { + key: 'parseMarkers', + value: function parseMarkers(markers, parent) { + var _this4 = this; + + markers.forEach(function (m) { + return _this4.parseMarker(m, parent); + }); + } + }, { + key: 'parseMarker', + value: function parseMarker(_ref7, parent) { + var _this5 = this; + + var _ref72 = _slicedToArray(_ref7, 3); + + var markerTypeIndexes = _ref72[0]; + var closeCount = _ref72[1]; + var value = _ref72[2]; + + markerTypeIndexes.forEach(function (index) { + _this5.markups.push(_this5.markerTypes[index]); + }); + var marker = this.builder.createMarker(value, this.markups.slice()); + parent.markers.append(marker); + this.markups = this.markups.slice(0, this.markups.length - closeCount); + } + }]); + + return MobiledocParser; + })(); + + exports['default'] = MobiledocParser; +}); +define('mobiledoc-kit/parsers/mobiledoc/0-3-1', ['exports', 'mobiledoc-kit/renderers/mobiledoc/0-3-1', 'mobiledoc-kit/utils/array-utils', 'mobiledoc-kit/utils/assert'], function (exports, _mobiledocKitRenderersMobiledoc031, _mobiledocKitUtilsArrayUtils, _mobiledocKitUtilsAssert) { + 'use strict'; + + var _slicedToArray = (function () { function sliceIterator(arr, i) { var _arr = []; var _n = true; var _d = false; var _e = undefined; try { for (var _i = arr[Symbol.iterator](), _s; !(_n = (_s = _i.next()).done); _n = true) { _arr.push(_s.value); if (i && _arr.length === i) break; } } catch (err) { _d = true; _e = err; } finally { try { if (!_n && _i['return']) _i['return'](); } finally { if (_d) throw _e; } } return _arr; } return function (arr, i) { if (Array.isArray(arr)) { return arr; } else if (Symbol.iterator in Object(arr)) { return sliceIterator(arr, i); } else { throw new TypeError('Invalid attempt to destructure non-iterable instance'); } }; })(); + + var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })(); + + function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } } + + /* + * Parses from mobiledoc -> post + */ + + var MobiledocParser = (function () { + function MobiledocParser(builder) { + _classCallCheck(this, MobiledocParser); + + this.builder = builder; + } + + /** + * @param {Mobiledoc} + * @return {Post} + */ + + _createClass(MobiledocParser, [{ + key: 'parse', + value: function parse(_ref) { + var version = _ref.version; + var sections = _ref.sections; + var markerTypes = _ref.markups; + var cardTypes = _ref.cards; + var atomTypes = _ref.atoms; + + try { + var post = this.builder.createPost(); + + this.markups = []; + this.markerTypes = this.parseMarkerTypes(markerTypes); + this.cardTypes = this.parseCardTypes(cardTypes); + this.atomTypes = this.parseAtomTypes(atomTypes); + this.parseSections(sections, post); + + return post; + } catch (e) { + (0, _mobiledocKitUtilsAssert['default'])('Unable to parse mobiledoc: ' + e.message, false); + } + } + }, { + key: 'parseMarkerTypes', + value: function parseMarkerTypes(markerTypes) { + var _this = this; + + return markerTypes.map(function (markerType) { + return _this.parseMarkerType(markerType); + }); + } + }, { + key: 'parseMarkerType', + value: function parseMarkerType(_ref2) { + var _ref22 = _slicedToArray(_ref2, 2); + + var tagName = _ref22[0]; + var attributesArray = _ref22[1]; + + var attributesObject = (0, _mobiledocKitUtilsArrayUtils.kvArrayToObject)(attributesArray || []); + return this.builder.createMarkup(tagName, attributesObject); + } + }, { + key: 'parseCardTypes', + value: function parseCardTypes(cardTypes) { + var _this2 = this; + + return cardTypes.map(function (cardType) { + return _this2.parseCardType(cardType); + }); + } + }, { + key: 'parseCardType', + value: function parseCardType(_ref3) { + var _ref32 = _slicedToArray(_ref3, 2); + + var cardName = _ref32[0]; + var cardPayload = _ref32[1]; + + return [cardName, cardPayload]; + } + }, { + key: 'parseAtomTypes', + value: function parseAtomTypes(atomTypes) { + var _this3 = this; + + return atomTypes.map(function (atomType) { + return _this3.parseAtomType(atomType); + }); + } + }, { + key: 'parseAtomType', + value: function parseAtomType(_ref4) { + var _ref42 = _slicedToArray(_ref4, 3); + + var atomName = _ref42[0]; + var atomValue = _ref42[1]; + var atomPayload = _ref42[2]; + + return [atomName, atomValue, atomPayload]; + } + }, { + key: 'parseSections', + value: function parseSections(sections, post) { + var _this4 = this; + + sections.forEach(function (section) { + return _this4.parseSection(section, post); + }); + } + }, { + key: 'parseSection', + value: function parseSection(section, post) { + var _section = _slicedToArray(section, 1); + + var type = _section[0]; + + switch (type) { + case _mobiledocKitRenderersMobiledoc031.MOBILEDOC_MARKUP_SECTION_TYPE: + this.parseMarkupSection(section, post); + break; + case _mobiledocKitRenderersMobiledoc031.MOBILEDOC_IMAGE_SECTION_TYPE: + this.parseImageSection(section, post); + break; + case _mobiledocKitRenderersMobiledoc031.MOBILEDOC_CARD_SECTION_TYPE: + this.parseCardSection(section, post); + break; + case _mobiledocKitRenderersMobiledoc031.MOBILEDOC_LIST_SECTION_TYPE: + this.parseListSection(section, post); + break; + default: + (0, _mobiledocKitUtilsAssert['default'])('Unexpected section type ${type}', false); + } + } + }, { + key: 'getAtomTypeFromIndex', + value: function getAtomTypeFromIndex(index) { + var atomType = this.atomTypes[index]; + (0, _mobiledocKitUtilsAssert['default'])('No atom definition found at index ' + index, !!atomType); + return atomType; + } + }, { + key: 'getCardTypeFromIndex', + value: function getCardTypeFromIndex(index) { + var cardType = this.cardTypes[index]; + (0, _mobiledocKitUtilsAssert['default'])('No card definition found at index ' + index, !!cardType); + return cardType; + } + }, { + key: 'parseCardSection', + value: function parseCardSection(_ref5, post) { + var _ref52 = _slicedToArray(_ref5, 2); + + var type = _ref52[0]; + var cardIndex = _ref52[1]; + + var _getCardTypeFromIndex = this.getCardTypeFromIndex(cardIndex); + + var _getCardTypeFromIndex2 = _slicedToArray(_getCardTypeFromIndex, 2); + + var name = _getCardTypeFromIndex2[0]; + var payload = _getCardTypeFromIndex2[1]; + + var section = this.builder.createCardSection(name, payload); + post.sections.append(section); + } + }, { + key: 'parseImageSection', + value: function parseImageSection(_ref6, post) { + var _ref62 = _slicedToArray(_ref6, 2); + + var type = _ref62[0]; + var src = _ref62[1]; + + var section = this.builder.createImageSection(src); + post.sections.append(section); + } + }, { + key: 'parseMarkupSection', + value: function parseMarkupSection(_ref7, post) { + var _ref72 = _slicedToArray(_ref7, 3); + + var type = _ref72[0]; + var tagName = _ref72[1]; + var markers = _ref72[2]; var section = this.builder.createMarkupSection(tagName); post.sections.append(section); @@ -8428,12 +8856,12 @@ define('mobiledoc-kit/parsers/mobiledoc/0-2', ['exports', 'mobiledoc-kit/rendere } }, { key: 'parseListSection', - value: function parseListSection(_ref6, post) { - var _ref62 = _slicedToArray(_ref6, 3); + value: function parseListSection(_ref8, post) { + var _ref82 = _slicedToArray(_ref8, 3); - var type = _ref62[0]; - var tagName = _ref62[1]; - var items = _ref62[2]; + var type = _ref82[0]; + var tagName = _ref82[1]; + var items = _ref82[2]; var section = this.builder.createListSection(tagName); post.sections.append(section); @@ -8442,10 +8870,10 @@ define('mobiledoc-kit/parsers/mobiledoc/0-2', ['exports', 'mobiledoc-kit/rendere }, { key: 'parseListItems', value: function parseListItems(items, section) { - var _this3 = this; + var _this5 = this; items.forEach(function (i) { - return _this3.parseListItem(i, section); + return _this5.parseListItem(i, section); }); } }, { @@ -8458,30 +8886,51 @@ define('mobiledoc-kit/parsers/mobiledoc/0-2', ['exports', 'mobiledoc-kit/rendere }, { key: 'parseMarkers', value: function parseMarkers(markers, parent) { - var _this4 = this; + var _this6 = this; markers.forEach(function (m) { - return _this4.parseMarker(m, parent); + return _this6.parseMarker(m, parent); }); } }, { key: 'parseMarker', - value: function parseMarker(_ref7, parent) { - var _this5 = this; + value: function parseMarker(_ref9, parent) { + var _this7 = this; - var _ref72 = _slicedToArray(_ref7, 3); + var _ref92 = _slicedToArray(_ref9, 4); - var markerTypeIndexes = _ref72[0]; - var closeCount = _ref72[1]; - var value = _ref72[2]; + var type = _ref92[0]; + var markerTypeIndexes = _ref92[1]; + var closeCount = _ref92[2]; + var value = _ref92[3]; markerTypeIndexes.forEach(function (index) { - _this5.markups.push(_this5.markerTypes[index]); + _this7.markups.push(_this7.markerTypes[index]); }); - var marker = this.builder.createMarker(value, this.markups.slice()); + + var marker = this.buildMarkerType(type, value); parent.markers.append(marker); + this.markups = this.markups.slice(0, this.markups.length - closeCount); } + }, { + key: 'buildMarkerType', + value: function buildMarkerType(type, value) { + switch (type) { + case _mobiledocKitRenderersMobiledoc031.MOBILEDOC_MARKUP_MARKER_TYPE: + return this.builder.createMarker(value, this.markups.slice()); + case _mobiledocKitRenderersMobiledoc031.MOBILEDOC_ATOM_MARKER_TYPE: + var _getAtomTypeFromIndex = this.getAtomTypeFromIndex(value), + _getAtomTypeFromIndex2 = _slicedToArray(_getAtomTypeFromIndex, 3), + atomName = _getAtomTypeFromIndex2[0], + atomValue = _getAtomTypeFromIndex2[1], + atomPayload = _getAtomTypeFromIndex2[2]; + + return this.builder.createAtom(atomName, atomValue, atomPayload, this.markups.slice()); + default: + (0, _mobiledocKitUtilsAssert['default'])('Unexpected marker type ' + type, false); + } + } }]); return MobiledocParser; @@ -8681,7 +9130,7 @@ define('mobiledoc-kit/parsers/mobiledoc/0-3', ['exports', 'mobiledoc-kit/rendere var tagName = _ref72[1]; var markers = _ref72[2]; - var section = this.builder.createMarkupSection(tagName); + var section = this.builder.createMarkupSection(tagName.toLowerCase() === 'pull-quote' ? 'aside' : tagName); post.sections.append(section); this.parseMarkers(markers, section); // Strip blank markers after they have been created. This ensures any @@ -8776,7 +9225,7 @@ define('mobiledoc-kit/parsers/mobiledoc/0-3', ['exports', 'mobiledoc-kit/rendere exports['default'] = MobiledocParser; }); -define('mobiledoc-kit/parsers/mobiledoc', ['exports', 'mobiledoc-kit/parsers/mobiledoc/0-2', 'mobiledoc-kit/parsers/mobiledoc/0-3', 'mobiledoc-kit/renderers/mobiledoc/0-2', 'mobiledoc-kit/renderers/mobiledoc/0-3', 'mobiledoc-kit/utils/assert'], function (exports, _mobiledocKitParsersMobiledoc02, _mobiledocKitParsersMobiledoc03, _mobiledocKitRenderersMobiledoc02, _mobiledocKitRenderersMobiledoc03, _mobiledocKitUtilsAssert) { +define('mobiledoc-kit/parsers/mobiledoc', ['exports', 'mobiledoc-kit/parsers/mobiledoc/0-2', 'mobiledoc-kit/parsers/mobiledoc/0-3', 'mobiledoc-kit/parsers/mobiledoc/0-3-1', 'mobiledoc-kit/renderers/mobiledoc/0-2', 'mobiledoc-kit/renderers/mobiledoc/0-3', 'mobiledoc-kit/renderers/mobiledoc/0-3-1', 'mobiledoc-kit/utils/assert'], function (exports, _mobiledocKitParsersMobiledoc02, _mobiledocKitParsersMobiledoc03, _mobiledocKitParsersMobiledoc031, _mobiledocKitRenderersMobiledoc02, _mobiledocKitRenderersMobiledoc03, _mobiledocKitRenderersMobiledoc031, _mobiledocKitUtilsAssert) { 'use strict'; function parseVersion(mobiledoc) { @@ -8791,6 +9240,8 @@ define('mobiledoc-kit/parsers/mobiledoc', ['exports', 'mobiledoc-kit/parsers/mob return new _mobiledocKitParsersMobiledoc02['default'](builder).parse(mobiledoc); case _mobiledocKitRenderersMobiledoc03.MOBILEDOC_VERSION: return new _mobiledocKitParsersMobiledoc03['default'](builder).parse(mobiledoc); + case _mobiledocKitRenderersMobiledoc031.MOBILEDOC_VERSION: + return new _mobiledocKitParsersMobiledoc031['default'](builder).parse(mobiledoc); default: (0, _mobiledocKitUtilsAssert['default'])('Unknown version of mobiledoc parser requested: ' + version, false); } @@ -9980,6 +10431,150 @@ define('mobiledoc-kit/renderers/mobiledoc/0-2', ['exports', 'mobiledoc-kit/utils } }; }); +define('mobiledoc-kit/renderers/mobiledoc/0-3-1', ['exports', 'mobiledoc-kit/utils/compiler', 'mobiledoc-kit/utils/array-utils', 'mobiledoc-kit/models/types'], function (exports, _mobiledocKitUtilsCompiler, _mobiledocKitUtilsArrayUtils, _mobiledocKitModelsTypes) { + 'use strict'; + + var _visitor; + + function _defineProperty(obj, key, value) { if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; } + + var MOBILEDOC_VERSION = '0.3.1'; + exports.MOBILEDOC_VERSION = MOBILEDOC_VERSION; + var MOBILEDOC_MARKUP_SECTION_TYPE = 1; + exports.MOBILEDOC_MARKUP_SECTION_TYPE = MOBILEDOC_MARKUP_SECTION_TYPE; + var MOBILEDOC_IMAGE_SECTION_TYPE = 2; + exports.MOBILEDOC_IMAGE_SECTION_TYPE = MOBILEDOC_IMAGE_SECTION_TYPE; + var MOBILEDOC_LIST_SECTION_TYPE = 3; + exports.MOBILEDOC_LIST_SECTION_TYPE = MOBILEDOC_LIST_SECTION_TYPE; + var MOBILEDOC_CARD_SECTION_TYPE = 10; + + exports.MOBILEDOC_CARD_SECTION_TYPE = MOBILEDOC_CARD_SECTION_TYPE; + var MOBILEDOC_MARKUP_MARKER_TYPE = 0; + exports.MOBILEDOC_MARKUP_MARKER_TYPE = MOBILEDOC_MARKUP_MARKER_TYPE; + var MOBILEDOC_ATOM_MARKER_TYPE = 1; + + exports.MOBILEDOC_ATOM_MARKER_TYPE = MOBILEDOC_ATOM_MARKER_TYPE; + var visitor = (_visitor = {}, _defineProperty(_visitor, _mobiledocKitModelsTypes.POST_TYPE, function (node, opcodes) { + opcodes.push(['openPost']); + (0, _mobiledocKitUtilsCompiler.visitArray)(visitor, node.sections, opcodes); + }), _defineProperty(_visitor, _mobiledocKitModelsTypes.MARKUP_SECTION_TYPE, function (node, opcodes) { + opcodes.push(['openMarkupSection', node.tagName]); + (0, _mobiledocKitUtilsCompiler.visitArray)(visitor, node.markers, opcodes); + }), _defineProperty(_visitor, _mobiledocKitModelsTypes.LIST_SECTION_TYPE, function (node, opcodes) { + opcodes.push(['openListSection', node.tagName]); + (0, _mobiledocKitUtilsCompiler.visitArray)(visitor, node.items, opcodes); + }), _defineProperty(_visitor, _mobiledocKitModelsTypes.LIST_ITEM_TYPE, function (node, opcodes) { + opcodes.push(['openListItem']); + (0, _mobiledocKitUtilsCompiler.visitArray)(visitor, node.markers, opcodes); + }), _defineProperty(_visitor, _mobiledocKitModelsTypes.IMAGE_SECTION_TYPE, function (node, opcodes) { + opcodes.push(['openImageSection', node.src]); + }), _defineProperty(_visitor, _mobiledocKitModelsTypes.CARD_TYPE, function (node, opcodes) { + opcodes.push(['openCardSection', node.name, node.payload]); + }), _defineProperty(_visitor, _mobiledocKitModelsTypes.MARKER_TYPE, function (node, opcodes) { + opcodes.push(['openMarker', node.closedMarkups.length, node.value]); + (0, _mobiledocKitUtilsCompiler.visitArray)(visitor, node.openedMarkups, opcodes); + }), _defineProperty(_visitor, _mobiledocKitModelsTypes.MARKUP_TYPE, function (node, opcodes) { + opcodes.push(['openMarkup', node.tagName, (0, _mobiledocKitUtilsArrayUtils.objectToSortedKVArray)(node.attributes)]); + }), _defineProperty(_visitor, _mobiledocKitModelsTypes.ATOM_TYPE, function (node, opcodes) { + opcodes.push(['openAtom', node.closedMarkups.length, node.name, node.value, node.payload]); + (0, _mobiledocKitUtilsCompiler.visitArray)(visitor, node.openedMarkups, opcodes); + }), _visitor); + + var postOpcodeCompiler = { + openMarker: function openMarker(closeCount, value) { + this.markupMarkerIds = []; + this.markers.push([MOBILEDOC_MARKUP_MARKER_TYPE, this.markupMarkerIds, closeCount, value || '']); + }, + openMarkupSection: function openMarkupSection(tagName) { + this.markers = []; + this.sections.push([MOBILEDOC_MARKUP_SECTION_TYPE, tagName, this.markers]); + }, + openListSection: function openListSection(tagName) { + this.items = []; + this.sections.push([MOBILEDOC_LIST_SECTION_TYPE, tagName, this.items]); + }, + openListItem: function openListItem() { + this.markers = []; + this.items.push(this.markers); + }, + openImageSection: function openImageSection(url) { + this.sections.push([MOBILEDOC_IMAGE_SECTION_TYPE, url]); + }, + openCardSection: function openCardSection(name, payload) { + var index = this._addCardTypeIndex(name, payload); + this.sections.push([MOBILEDOC_CARD_SECTION_TYPE, index]); + }, + openAtom: function openAtom(closeCount, name, value, payload) { + var index = this._addAtomTypeIndex(name, value, payload); + this.markupMarkerIds = []; + this.markers.push([MOBILEDOC_ATOM_MARKER_TYPE, this.markupMarkerIds, closeCount, index]); + }, + openPost: function openPost() { + this.atomTypes = []; + this.cardTypes = []; + this.markerTypes = []; + this.sections = []; + this.result = { + version: MOBILEDOC_VERSION, + atoms: this.atomTypes, + cards: this.cardTypes, + markups: this.markerTypes, + sections: this.sections + }; + }, + openMarkup: function openMarkup(tagName, attributes) { + var index = this._findOrAddMarkerTypeIndex(tagName, attributes); + this.markupMarkerIds.push(index); + }, + _addCardTypeIndex: function _addCardTypeIndex(cardName, payload) { + var cardType = [cardName, payload]; + this.cardTypes.push(cardType); + return this.cardTypes.length - 1; + }, + _addAtomTypeIndex: function _addAtomTypeIndex(atomName, atomValue, payload) { + var atomType = [atomName, atomValue, payload]; + this.atomTypes.push(atomType); + return this.atomTypes.length - 1; + }, + _findOrAddMarkerTypeIndex: function _findOrAddMarkerTypeIndex(tagName, attributesArray) { + if (!this._markerTypeCache) { + this._markerTypeCache = {}; + } + var key = tagName + '-' + attributesArray.join('-'); + + var index = this._markerTypeCache[key]; + if (index === undefined) { + var markerType = [tagName]; + if (attributesArray.length) { + markerType.push(attributesArray); + } + this.markerTypes.push(markerType); + + index = this.markerTypes.length - 1; + this._markerTypeCache[key] = index; + } + + return index; + } + }; + + /** + * Render from post -> mobiledoc + */ + exports['default'] = { + /** + * @param {Post} + * @return {Mobiledoc} + */ + render: function render(post) { + var opcodes = []; + (0, _mobiledocKitUtilsCompiler.visit)(visitor, post, opcodes); + var compiler = Object.create(postOpcodeCompiler); + (0, _mobiledocKitUtilsCompiler.compile)(compiler, opcodes); + return compiler.result; + } + }; +}); define('mobiledoc-kit/renderers/mobiledoc/0-3', ['exports', 'mobiledoc-kit/utils/compiler', 'mobiledoc-kit/utils/array-utils', 'mobiledoc-kit/models/types'], function (exports, _mobiledocKitUtilsCompiler, _mobiledocKitUtilsArrayUtils, _mobiledocKitModelsTypes) { 'use strict'; @@ -10124,10 +10719,10 @@ define('mobiledoc-kit/renderers/mobiledoc/0-3', ['exports', 'mobiledoc-kit/utils } }; }); -define('mobiledoc-kit/renderers/mobiledoc', ['exports', 'mobiledoc-kit/renderers/mobiledoc/0-2', 'mobiledoc-kit/renderers/mobiledoc/0-3', 'mobiledoc-kit/utils/assert'], function (exports, _mobiledocKitRenderersMobiledoc02, _mobiledocKitRenderersMobiledoc03, _mobiledocKitUtilsAssert) { +define('mobiledoc-kit/renderers/mobiledoc', ['exports', 'mobiledoc-kit/renderers/mobiledoc/0-2', 'mobiledoc-kit/renderers/mobiledoc/0-3', 'mobiledoc-kit/renderers/mobiledoc/0-3-1', 'mobiledoc-kit/utils/assert'], function (exports, _mobiledocKitRenderersMobiledoc02, _mobiledocKitRenderersMobiledoc03, _mobiledocKitRenderersMobiledoc031, _mobiledocKitUtilsAssert) { 'use strict'; - var MOBILEDOC_VERSION = _mobiledocKitRenderersMobiledoc03.MOBILEDOC_VERSION; + var MOBILEDOC_VERSION = _mobiledocKitRenderersMobiledoc031.MOBILEDOC_VERSION; exports.MOBILEDOC_VERSION = MOBILEDOC_VERSION; exports['default'] = { @@ -10135,10 +10730,12 @@ define('mobiledoc-kit/renderers/mobiledoc', ['exports', 'mobiledoc-kit/renderers switch (version) { case _mobiledocKitRenderersMobiledoc02.MOBILEDOC_VERSION: return _mobiledocKitRenderersMobiledoc02['default'].render(post); - case undefined: - case null: case _mobiledocKitRenderersMobiledoc03.MOBILEDOC_VERSION: return _mobiledocKitRenderersMobiledoc03['default'].render(post); + case undefined: + case null: + case _mobiledocKitRenderersMobiledoc031.MOBILEDOC_VERSION: + return _mobiledocKitRenderersMobiledoc031['default'].render(post); default: (0, _mobiledocKitUtilsAssert['default'])('Unknown version of mobiledoc renderer requested: ' + version, false); } @@ -10636,6 +11233,9 @@ define('mobiledoc-kit/utils/cursor', ['exports', 'mobiledoc-kit/utils/selection- var selection = this.selection; var renderTree = this.renderTree; + var parentNode = this.editor.element; + selection = (0, _mobiledocKitUtilsSelectionUtils.constrainSelectionTo)(selection, parentNode); + var _comparePosition = (0, _mobiledocKitUtilsSelectionUtils.comparePosition)(selection); var headNode = _comparePosition.headNode; @@ -10674,7 +11274,7 @@ define('mobiledoc-kit/utils/cursor', ['exports', 'mobiledoc-kit/utils/selection- define('mobiledoc-kit/utils/cursor/position', ['exports', 'mobiledoc-kit/utils/dom-utils', 'mobiledoc-kit/utils/assert', 'mobiledoc-kit/models/marker', 'mobiledoc-kit/utils/selection-utils', 'mobiledoc-kit/utils/key', 'mobiledoc-kit/utils/cursor/range'], function (exports, _mobiledocKitUtilsDomUtils, _mobiledocKitUtilsAssert, _mobiledocKitModelsMarker, _mobiledocKitUtilsSelectionUtils, _mobiledocKitUtilsKey, _mobiledocKitUtilsCursorRange) { 'use strict'; - var _get = function get(_x4, _x5, _x6) { var _again = true; _function: while (_again) { var object = _x4, property = _x5, receiver = _x6; _again = false; if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { _x4 = parent; _x5 = property; _x6 = receiver; _again = true; desc = parent = undefined; continue _function; } } else if ('value' in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } } }; + var _get = function get(_x5, _x6, _x7) { var _again = true; _function: while (_again) { var object = _x5, property = _x6, receiver = _x7; _again = false; if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { _x5 = parent; _x6 = property; _x7 = receiver; _again = true; desc = parent = undefined; continue _function; } } else if ('value' in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } } }; var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })(); @@ -10778,8 +11378,9 @@ define('mobiledoc-kit/utils/cursor/position', ['exports', 'mobiledoc-kit/utils/d */ value: function toRange() { var tail = arguments.length <= 0 || arguments[0] === undefined ? this : arguments[0]; + var direction = arguments.length <= 1 || arguments[1] === undefined ? null : arguments[1]; - return new _mobiledocKitUtilsCursorRange['default'](this, tail); + return new _mobiledocKitUtilsCursorRange['default'](this, tail, direction); } }, { key: 'markerIn', @@ -10847,7 +11448,7 @@ define('mobiledoc-kit/utils/cursor/position', ['exports', 'mobiledoc-kit/utils/d } /** - * @return {Boolean} If this position is at the head of its section + * @return {Boolean} If this position is at the tail of its section */ }, { key: 'isTail', @@ -11361,6 +11962,41 @@ define('mobiledoc-kit/utils/cursor/range', ['exports', 'mobiledoc-kit/utils/curs return this._collapse(direction); } } + + /** + * expand a range to all markers matching a given check + * + * @param {Function} detectMarker + * @return {Range} The expanded range + * + * @public + */ + }, { + key: 'expandByMarker', + value: function expandByMarker(detectMarker) { + var head = this.head; + var tail = this.tail; + var direction = this.direction; + var headSection = head.section; + + if (headSection !== tail.section) { + throw new Error('#expandByMarker does not work across sections. Perhaps you should confirm the range is collapsed'); + } + + var firstNotMatchingDetect = function firstNotMatchingDetect(i) { + return !detectMarker(i); + }; + + var headMarker = head.section.markers.detect(firstNotMatchingDetect, head.marker, true); + headMarker = headMarker && headMarker.next || head.marker; + var headPosition = new _mobiledocKitUtilsCursorPosition['default'](headSection, headSection.offsetOfMarker(headMarker)); + + var tailMarker = tail.section.markers.detect(firstNotMatchingDetect, tail.marker); + tailMarker = tailMarker && tailMarker.prev || tail.marker; + var tailPosition = new _mobiledocKitUtilsCursorPosition['default'](tail.section, tail.section.offsetOfMarker(tailMarker) + tailMarker.length); + + return headPosition.toRange(tailPosition, direction); + } }, { key: '_collapse', value: function _collapse(direction) { @@ -11584,6 +12220,12 @@ define('mobiledoc-kit/utils/dom-utils', ['exports', 'mobiledoc-kit/utils/array-u return div; } + function serializeHTML(node) { + var div = document.createElement('div'); + div.appendChild(node); + return div.innerHTML; + } + exports.containsNode = containsNode; exports.clearChildNodes = clearChildNodes; exports.getAttributes = getAttributes; @@ -11596,6 +12238,7 @@ define('mobiledoc-kit/utils/dom-utils', ['exports', 'mobiledoc-kit/utils/array-u exports.isCommentNode = isCommentNode; exports.isElementNode = isElementNode; exports.parseHTML = parseHTML; + exports.serializeHTML = serializeHTML; }); define('mobiledoc-kit/utils/element-map', ['exports', 'mobiledoc-kit/utils/assert'], function (exports, _mobiledocKitUtilsAssert) { 'use strict'; @@ -11718,6 +12361,15 @@ define('mobiledoc-kit/utils/element-utils', ['exports', 'mobiledoc-kit/utils/str exports.positionElementHorizontallyCenteredToRect = positionElementHorizontallyCenteredToRect; exports.positionElementCenteredBelow = positionElementCenteredBelow; }); +define('mobiledoc-kit/utils/environment', ['exports'], function (exports) { + 'use strict'; + + exports['default'] = { + hasDOM: function hasDOM() { + return typeof document !== 'undefined'; + } + }; +}); define("mobiledoc-kit/utils/fixed-queue", ["exports"], function (exports) { "use strict"; @@ -12305,12 +12957,13 @@ define('mobiledoc-kit/utils/linked-list', ['exports', 'mobiledoc-kit/utils/asser key: 'detect', value: function detect(callback) { var item = arguments.length <= 1 || arguments[1] === undefined ? this.head : arguments[1]; + var reverse = arguments.length <= 2 || arguments[2] === undefined ? false : arguments[2]; while (item) { if (callback(item)) { return item; } - item = item.next; + item = reverse ? item.prev : item.next; } } }, { @@ -12935,6 +13588,54 @@ define('mobiledoc-kit/utils/selection-utils', ['exports', 'mobiledoc-kit/utils/k } } + function constrainNodeTo(node, parentNode, existingOffset) { + var compare = parentNode.compareDocumentPosition(node); + if (compare & Node.DOCUMENT_POSITION_CONTAINED_BY) { + // the node is inside parentNode, do nothing + return { node: node, offset: existingOffset }; + } else if (compare & Node.DOCUMENT_POSITION_CONTAINS) { + // the node contains parentNode. This shouldn't happen. + return { node: node, offset: existingOffset }; + } else if (compare & Node.DOCUMENT_POSITION_PRECEDING) { + // node is before parentNode. return start of deepest first child + var child = parentNode.firstChild; + while (child.firstChild) { + child = child.firstChild; + } + return { node: child, offset: 0 }; + } else if (compare & Node.DOCUMENT_POSITION_FOLLOWING) { + // node is after parentNode. return end of deepest last child + var child = parentNode.lastChild; + while (child.lastChild) { + child = child.lastChild; + } + + var offset = (0, _mobiledocKitUtilsDomUtils.isTextNode)(child) ? child.textContent.length : 1; + return { node: child, offset: offset }; + } else { + return { node: node, offset: existingOffset }; + } + } + + /* + * Returns a new selection that is constrained within parentNode. + * If the anchorNode or focusNode are outside the parentNode, they are replaced with the beginning + * or end of the parentNode's children + */ + function constrainSelectionTo(selection, parentNode) { + var _constrainNodeTo = constrainNodeTo(selection.anchorNode, parentNode, selection.anchorOffset); + + var anchorNode = _constrainNodeTo.node; + var anchorOffset = _constrainNodeTo.offset; + + var _constrainNodeTo2 = constrainNodeTo(selection.focusNode, parentNode, selection.focusOffset); + + var focusNode = _constrainNodeTo2.node; + var focusOffset = _constrainNodeTo2.offset; + + return { anchorNode: anchorNode, anchorOffset: anchorOffset, focusNode: focusNode, focusOffset: focusOffset }; + } + function comparePosition(_x3) { var _again2 = true; @@ -13034,6 +13735,7 @@ define('mobiledoc-kit/utils/selection-utils', ['exports', 'mobiledoc-kit/utils/k exports.clearSelection = clearSelection; exports.comparePosition = comparePosition; exports.findOffsetInNode = findOffsetInNode; + exports.constrainSelectionTo = constrainSelectionTo; }); define("mobiledoc-kit/utils/set", ["exports"], function (exports) { "use strict"; @@ -13138,7 +13840,7 @@ define('mobiledoc-kit/utils/to-range', ['exports', 'mobiledoc-kit/utils/cursor/r define('mobiledoc-kit/version', ['exports'], function (exports) { 'use strict'; - exports['default'] = '0.10.11'; + exports['default'] = '0.10.16'; }); define('mobiledoc-kit/views/tooltip', ['exports', 'mobiledoc-kit/views/view', 'mobiledoc-kit/utils/element-utils'], function (exports, _mobiledocKitViewsView, _mobiledocKitUtilsElementUtils) { 'use strict'; @@ -13382,10 +14084,11 @@ define('mobiledoc-text-renderer/renderer-factory', ['exports', 'mobiledoc-text-r switch (version) { case _mobiledocTextRendererRenderers02.MOBILEDOC_VERSION: + return new _mobiledocTextRendererRenderers02['default'](mobiledoc, this.state).render(); case undefined: case null: - return new _mobiledocTextRendererRenderers02['default'](mobiledoc, this.state).render(); - case _mobiledocTextRendererRenderers03.MOBILEDOC_VERSION: + case _mobiledocTextRendererRenderers03.MOBILEDOC_VERSION_0_3: + case _mobiledocTextRendererRenderers03.MOBILEDOC_VERSION_0_3_1: return new _mobiledocTextRendererRenderers03['default'](mobiledoc, this.state).render(); default: throw new Error('Unexpected Mobiledoc version "' + version + '"'); @@ -13649,11 +14352,15 @@ define('mobiledoc-text-renderer/renderers/0-3', ['exports', 'mobiledoc-text-rend var LINE_BREAK = '\n'; - var MOBILEDOC_VERSION = '0.3.0'; + var MOBILEDOC_VERSION_0_3 = '0.3.0'; + exports.MOBILEDOC_VERSION_0_3 = MOBILEDOC_VERSION_0_3; + var MOBILEDOC_VERSION_0_3_1 = '0.3.1'; + exports.MOBILEDOC_VERSION_0_3_1 = MOBILEDOC_VERSION_0_3_1; + var MOBILEDOC_VERSION = MOBILEDOC_VERSION_0_3_1; exports.MOBILEDOC_VERSION = MOBILEDOC_VERSION; function validateVersion(version) { - if (version !== MOBILEDOC_VERSION) { + if (version !== MOBILEDOC_VERSION_0_3 && version !== MOBILEDOC_VERSION_0_3_1) { throw new Error('Unexpected Mobiledoc version "' + version + '"'); } } @@ -14017,4 +14724,4 @@ define("mobiledoc-text-renderer/utils/section-types", ["exports"], function (exp exports.LIST_SECTION_TYPE = LIST_SECTION_TYPE; var CARD_SECTION_TYPE = 10; exports.CARD_SECTION_TYPE = CARD_SECTION_TYPE; -});//# sourceMappingURL=mobiledoc-kit.map \ No newline at end of file +});//# sourceMappingURL=mobiledoc-kit.map diff --git a/website/amd/mobiledoc-kit.map b/website/amd/mobiledoc-kit.map index 629b58b80..b02184c16 100644 --- a/website/amd/mobiledoc-kit.map +++ b/website/amd/mobiledoc-kit.map @@ -1 +1 @@ -{"version":3,"sources":["mobiledoc-html-renderer/cards/image.js","mobiledoc-html-renderer/index.js","mobiledoc-html-renderer/renderer-factory.js","mobiledoc-html-renderer/renderers/0-2.js","mobiledoc-html-renderer/renderers/0-3.js","mobiledoc-html-renderer/utils/dom.js","mobiledoc-html-renderer/utils/marker-types.js","mobiledoc-html-renderer/utils/render-type.js","mobiledoc-html-renderer/utils/section-types.js","mobiledoc-html-renderer/utils/tag-names.js","mobiledoc-kit/cards/image.js","mobiledoc-kit/editor/edit-history.js","mobiledoc-kit/editor/edit-state.js","mobiledoc-kit/editor/editor.js","mobiledoc-kit/editor/event-manager.js","mobiledoc-kit/editor/key-commands.js","mobiledoc-kit/editor/mutation-handler.js","mobiledoc-kit/editor/post.js","mobiledoc-kit/editor/post/post-inserter.js","mobiledoc-kit/editor/selection-change-observer.js","mobiledoc-kit/editor/selection-manager.js","mobiledoc-kit/editor/text-input-handler.js","mobiledoc-kit/editor/text-input-handlers.js","mobiledoc-kit/editor/ui.js","mobiledoc-kit/index.js","mobiledoc-kit/models/_markerable.js","mobiledoc-kit/models/_section.js","mobiledoc-kit/models/atom-node.js","mobiledoc-kit/models/atom.js","mobiledoc-kit/models/card-node.js","mobiledoc-kit/models/card.js","mobiledoc-kit/models/image.js","mobiledoc-kit/models/lifecycle-callbacks.js","mobiledoc-kit/models/list-item.js","mobiledoc-kit/models/list-section.js","mobiledoc-kit/models/marker.js","mobiledoc-kit/models/markup-section.js","mobiledoc-kit/models/markup.js","mobiledoc-kit/models/post-node-builder.js","mobiledoc-kit/models/post.js","mobiledoc-kit/models/render-node.js","mobiledoc-kit/models/render-tree.js","mobiledoc-kit/models/types.js","mobiledoc-kit/parsers/dom.js","mobiledoc-kit/parsers/html.js","mobiledoc-kit/parsers/mobiledoc/0-2.js","mobiledoc-kit/parsers/mobiledoc/0-3.js","mobiledoc-kit/parsers/mobiledoc/index.js","mobiledoc-kit/parsers/section.js","mobiledoc-kit/parsers/text.js","mobiledoc-kit/renderers/editor-dom.js","mobiledoc-kit/renderers/mobiledoc/0-2.js","mobiledoc-kit/renderers/mobiledoc/0-3.js","mobiledoc-kit/renderers/mobiledoc/index.js","mobiledoc-kit/utils/array-utils.js","mobiledoc-kit/utils/assert.js","mobiledoc-kit/utils/browser.js","mobiledoc-kit/utils/characters.js","mobiledoc-kit/utils/compiler.js","mobiledoc-kit/utils/copy.js","mobiledoc-kit/utils/cursor.js","mobiledoc-kit/utils/cursor/position.js","mobiledoc-kit/utils/cursor/range.js","mobiledoc-kit/utils/deprecate.js","mobiledoc-kit/utils/dom-utils.js","mobiledoc-kit/utils/element-map.js","mobiledoc-kit/utils/element-utils.js","mobiledoc-kit/utils/fixed-queue.js","mobiledoc-kit/utils/key.js","mobiledoc-kit/utils/keycodes.js","mobiledoc-kit/utils/linked-item.js","mobiledoc-kit/utils/linked-list.js","mobiledoc-kit/utils/log-manager.js","mobiledoc-kit/utils/markuperable.js","mobiledoc-kit/utils/merge.js","mobiledoc-kit/utils/mixin.js","mobiledoc-kit/utils/mobiledoc-error.js","mobiledoc-kit/utils/parse-utils.js","mobiledoc-kit/utils/placeholder-image-src.js","mobiledoc-kit/utils/selection-utils.js","mobiledoc-kit/utils/set.js","mobiledoc-kit/utils/string-utils.js","mobiledoc-kit/utils/to-range.js","mobiledoc-kit/version.js","mobiledoc-kit/views/tooltip.js","mobiledoc-kit/views/view.js","mobiledoc-text-renderer/cards/image.js","mobiledoc-text-renderer/index.js","mobiledoc-text-renderer/renderer-factory.js","mobiledoc-text-renderer/renderers/0-2.js","mobiledoc-text-renderer/renderers/0-3.js","mobiledoc-text-renderer/utils/marker-types.js","mobiledoc-text-renderer/utils/render-type.js","mobiledoc-text-renderer/utils/section-types.js"],"sourcesContent":["define('mobiledoc-html-renderer/cards/image', ['exports', 'mobiledoc-html-renderer/utils/render-type'], function (exports, _mobiledocHtmlRendererUtilsRenderType) {\n 'use strict';\n\n exports['default'] = {\n name: 'image-card',\n type: _mobiledocHtmlRendererUtilsRenderType['default'],\n render: function render(_ref) {\n var env = _ref.env;\n var options = _ref.options;\n var payload = _ref.payload;\n\n if (payload.src) {\n return '';\n }\n }\n };\n});","define('mobiledoc-html-renderer', ['exports', 'mobiledoc-html-renderer/renderer-factory', 'mobiledoc-html-renderer/utils/render-type'], function (exports, _mobiledocHtmlRendererRendererFactory, _mobiledocHtmlRendererUtilsRenderType) {\n 'use strict';\n\n exports.registerGlobal = registerGlobal;\n\n function registerGlobal(window) {\n window.MobiledocHTMLRenderer = _mobiledocHtmlRendererRendererFactory['default'];\n }\n\n exports.RENDER_TYPE = _mobiledocHtmlRendererUtilsRenderType['default'];\n exports['default'] = _mobiledocHtmlRendererRendererFactory['default'];\n});","define('mobiledoc-html-renderer/renderer-factory', ['exports', 'mobiledoc-html-renderer/renderers/0-2', 'mobiledoc-html-renderer/renderers/0-3', 'mobiledoc-html-renderer/utils/render-type'], function (exports, _mobiledocHtmlRendererRenderers02, _mobiledocHtmlRendererRenderers03, _mobiledocHtmlRendererUtilsRenderType) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n function validateCards(cards) {\n if (!Array.isArray(cards)) {\n throw new Error('`cards` must be passed as an array');\n }\n for (var i = 0; i < cards.length; i++) {\n var card = cards[i];\n if (card.type !== _mobiledocHtmlRendererUtilsRenderType['default']) {\n throw new Error('Card \"' + card.name + '\" must be of type \"' + _mobiledocHtmlRendererUtilsRenderType['default'] + '\", was \"' + card.type + '\"');\n }\n if (!card.render) {\n throw new Error('Card \"' + card.name + '\" must define `render`');\n }\n }\n }\n\n function validateAtoms(atoms) {\n if (!Array.isArray(atoms)) {\n throw new Error('`atoms` must be passed as an array');\n }\n for (var i = 0; i < atoms.length; i++) {\n var atom = atoms[i];\n if (atom.type !== _mobiledocHtmlRendererUtilsRenderType['default']) {\n throw new Error('Atom \"' + atom.name + '\" must be type \"' + _mobiledocHtmlRendererUtilsRenderType['default'] + '\", was \"' + atom.type + '\"');\n }\n if (!atom.render) {\n throw new Error('Atom \"' + atom.name + '\" must define `render`');\n }\n }\n }\n\n var RendererFactory = (function () {\n function RendererFactory() {\n var _ref = arguments.length <= 0 || arguments[0] === undefined ? {} : arguments[0];\n\n var cards = _ref.cards;\n var atoms = _ref.atoms;\n var cardOptions = _ref.cardOptions;\n var unknownCardHandler = _ref.unknownCardHandler;\n var unknownAtomHandler = _ref.unknownAtomHandler;\n var sectionElementRenderer = _ref.sectionElementRenderer;\n\n _classCallCheck(this, RendererFactory);\n\n cards = cards || [];\n validateCards(cards);\n atoms = atoms || [];\n validateAtoms(atoms);\n cardOptions = cardOptions || {};\n\n this.state = {\n cards: cards,\n atoms: atoms,\n cardOptions: cardOptions,\n unknownCardHandler: unknownCardHandler,\n unknownAtomHandler: unknownAtomHandler,\n sectionElementRenderer: sectionElementRenderer\n };\n }\n\n _createClass(RendererFactory, [{\n key: 'render',\n value: function render(mobiledoc) {\n var version = mobiledoc.version;\n\n switch (version) {\n case _mobiledocHtmlRendererRenderers02.MOBILEDOC_VERSION:\n case undefined:\n case null:\n return new _mobiledocHtmlRendererRenderers02['default'](mobiledoc, this.state).render();\n case _mobiledocHtmlRendererRenderers03.MOBILEDOC_VERSION:\n return new _mobiledocHtmlRendererRenderers03['default'](mobiledoc, this.state).render();\n default:\n throw new Error('Unexpected Mobiledoc version \"' + version + '\"');\n }\n }\n }]);\n\n return RendererFactory;\n })();\n\n exports['default'] = RendererFactory;\n});","define('mobiledoc-html-renderer/renderers/0-2', ['exports', 'mobiledoc-html-renderer/utils/dom', 'mobiledoc-html-renderer/cards/image', 'mobiledoc-html-renderer/utils/render-type', 'mobiledoc-html-renderer/utils/section-types', 'mobiledoc-html-renderer/utils/tag-names'], function (exports, _mobiledocHtmlRendererUtilsDom, _mobiledocHtmlRendererCardsImage, _mobiledocHtmlRendererUtilsRenderType, _mobiledocHtmlRendererUtilsSectionTypes, _mobiledocHtmlRendererUtilsTagNames) {\n 'use strict';\n\n var _slicedToArray = (function () { function sliceIterator(arr, i) { var _arr = []; var _n = true; var _d = false; var _e = undefined; try { for (var _i = arr[Symbol.iterator](), _s; !(_n = (_s = _i.next()).done); _n = true) { _arr.push(_s.value); if (i && _arr.length === i) break; } } catch (err) { _d = true; _e = err; } finally { try { if (!_n && _i['return']) _i['return'](); } finally { if (_d) throw _e; } } return _arr; } return function (arr, i) { if (Array.isArray(arr)) { return arr; } else if (Symbol.iterator in Object(arr)) { return sliceIterator(arr, i); } else { throw new TypeError('Invalid attempt to destructure non-iterable instance'); } }; })();\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n var MOBILEDOC_VERSION = '0.2.0';\n\n exports.MOBILEDOC_VERSION = MOBILEDOC_VERSION;\n /**\n * runtime HTML renderer\n * renders a mobiledoc to HTML\n *\n * input: mobiledoc\n * output: HTML\n */\n\n function createElementFromMarkerType() {\n var _ref = arguments.length <= 0 || arguments[0] === undefined ? ['', []] : arguments[0];\n\n var _ref2 = _slicedToArray(_ref, 2);\n\n var tagName = _ref2[0];\n var attributes = _ref2[1];\n\n var element = (0, _mobiledocHtmlRendererUtilsDom.createElement)(tagName);\n attributes = attributes || [];\n\n for (var i = 0, l = attributes.length; i < l; i = i + 2) {\n var propName = attributes[i],\n propValue = attributes[i + 1];\n (0, _mobiledocHtmlRendererUtilsDom.setAttribute)(element, propName, propValue);\n }\n return element;\n }\n\n function validateVersion(version) {\n if (version !== MOBILEDOC_VERSION) {\n throw new Error('Unexpected Mobiledoc version \"' + version + '\"');\n }\n }\n\n var Renderer = (function () {\n function Renderer(mobiledoc, state) {\n _classCallCheck(this, Renderer);\n\n var cards = state.cards;\n var cardOptions = state.cardOptions;\n var unknownCardHandler = state.unknownCardHandler;\n var sectionElementRenderer = state.sectionElementRenderer;\n var version = mobiledoc.version;\n var sectionData = mobiledoc.sections;\n\n validateVersion(version);\n\n var _sectionData = _slicedToArray(sectionData, 2);\n\n var markerTypes = _sectionData[0];\n var sections = _sectionData[1];\n\n this.root = (0, _mobiledocHtmlRendererUtilsDom.createDocumentFragment)();\n this.markerTypes = markerTypes;\n this.sections = sections;\n this.cards = cards;\n this.cardOptions = cardOptions;\n this.unknownCardHandler = unknownCardHandler || this._defaultUnknownCardHandler;\n\n this.sectionElementRenderer = {};\n if (sectionElementRenderer) {\n for (var key in sectionElementRenderer) {\n if (sectionElementRenderer.hasOwnProperty(key)) {\n this.sectionElementRenderer[key.toLowerCase()] = sectionElementRenderer[key];\n }\n }\n }\n\n this._teardownCallbacks = [];\n }\n\n _createClass(Renderer, [{\n key: 'render',\n value: function render() {\n var _this = this;\n\n this.sections.forEach(function (section) {\n var rendered = _this.renderSection(section);\n if (rendered) {\n (0, _mobiledocHtmlRendererUtilsDom.appendChild)(_this.root, rendered);\n }\n });\n\n return { result: this.root.toString(), teardown: function teardown() {\n return _this.teardown();\n } };\n }\n }, {\n key: 'teardown',\n value: function teardown() {\n for (var i = 0; i < this._teardownCallbacks.length; i++) {\n this._teardownCallbacks[i]();\n }\n }\n }, {\n key: 'renderSection',\n value: function renderSection(section) {\n var _section = _slicedToArray(section, 1);\n\n var type = _section[0];\n\n switch (type) {\n case _mobiledocHtmlRendererUtilsSectionTypes.MARKUP_SECTION_TYPE:\n return this.renderMarkupSection(section);\n case _mobiledocHtmlRendererUtilsSectionTypes.IMAGE_SECTION_TYPE:\n return this.renderImageSection(section);\n case _mobiledocHtmlRendererUtilsSectionTypes.LIST_SECTION_TYPE:\n return this.renderListSection(section);\n case _mobiledocHtmlRendererUtilsSectionTypes.CARD_SECTION_TYPE:\n return this.renderCardSection(section);\n default:\n throw new Error('Renderer cannot render type \"' + type + '\"');\n }\n }\n }, {\n key: 'renderListSection',\n value: function renderListSection(_ref3) {\n var _this2 = this;\n\n var _ref32 = _slicedToArray(_ref3, 3);\n\n var type = _ref32[0];\n var tagName = _ref32[1];\n var items = _ref32[2];\n\n if (!(0, _mobiledocHtmlRendererUtilsTagNames.isValidSectionTagName)(tagName, _mobiledocHtmlRendererUtilsSectionTypes.LIST_SECTION_TYPE)) {\n return;\n }\n var element = (0, _mobiledocHtmlRendererUtilsDom.createElement)(tagName);\n items.forEach(function (li) {\n (0, _mobiledocHtmlRendererUtilsDom.appendChild)(element, _this2.renderListItem(li));\n });\n return element;\n }\n }, {\n key: 'renderListItem',\n value: function renderListItem(markers) {\n var element = (0, _mobiledocHtmlRendererUtilsDom.createElement)('li');\n this._renderMarkersOnElement(element, markers);\n return element;\n }\n }, {\n key: 'renderImageSection',\n value: function renderImageSection(_ref4) {\n var _ref42 = _slicedToArray(_ref4, 2);\n\n var type = _ref42[0];\n var url = _ref42[1];\n\n var element = (0, _mobiledocHtmlRendererUtilsDom.createElement)('img');\n (0, _mobiledocHtmlRendererUtilsDom.setAttribute)(element, 'src', url);\n return element;\n }\n }, {\n key: 'findCard',\n value: function findCard(name) {\n for (var i = 0; i < this.cards.length; i++) {\n if (this.cards[i].name === name) {\n return this.cards[i];\n }\n }\n if (name === _mobiledocHtmlRendererCardsImage['default'].name) {\n return _mobiledocHtmlRendererCardsImage['default'];\n }\n return this._createUnknownCard(name);\n }\n }, {\n key: '_createUnknownCard',\n value: function _createUnknownCard(name) {\n return {\n name: name,\n type: _mobiledocHtmlRendererUtilsRenderType['default'],\n render: this.unknownCardHandler\n };\n }\n }, {\n key: 'renderCardSection',\n value: function renderCardSection(_ref5) {\n var _ref52 = _slicedToArray(_ref5, 3);\n\n var type = _ref52[0];\n var name = _ref52[1];\n var payload = _ref52[2];\n\n var card = this.findCard(name);\n\n var cardWrapper = this._createCardElement();\n var cardArg = this._createCardArgument(card, payload);\n var rendered = card.render(cardArg);\n\n this._validateCardRender(rendered, card.name);\n\n if (rendered) {\n (0, _mobiledocHtmlRendererUtilsDom.appendChild)(cardWrapper, rendered);\n }\n\n return cardWrapper;\n }\n }, {\n key: '_registerTeardownCallback',\n value: function _registerTeardownCallback(callback) {\n this._teardownCallbacks.push(callback);\n }\n }, {\n key: '_createCardArgument',\n value: function _createCardArgument(card) {\n var _this3 = this;\n\n var payload = arguments.length <= 1 || arguments[1] === undefined ? {} : arguments[1];\n\n var env = {\n name: card.name,\n isInEditor: false,\n onTeardown: function onTeardown(callback) {\n return _this3._registerTeardownCallback(callback);\n }\n };\n\n var options = this.cardOptions;\n\n return { env: env, options: options, payload: payload };\n }\n }, {\n key: '_validateCardRender',\n value: function _validateCardRender(rendered, cardName) {\n if (!rendered) {\n return;\n }\n\n if (typeof rendered !== 'string') {\n throw new Error('Card \"' + cardName + '\" must render ' + _mobiledocHtmlRendererUtilsRenderType['default'] + ', but result was ' + typeof rendered + '\"');\n }\n }\n }, {\n key: '_createCardElement',\n value: function _createCardElement() {\n return (0, _mobiledocHtmlRendererUtilsDom.createElement)('div');\n }\n }, {\n key: 'renderMarkupSection',\n value: function renderMarkupSection(_ref6) {\n var _ref62 = _slicedToArray(_ref6, 3);\n\n var type = _ref62[0];\n var tagName = _ref62[1];\n var markers = _ref62[2];\n\n if (!(0, _mobiledocHtmlRendererUtilsTagNames.isValidSectionTagName)(tagName, _mobiledocHtmlRendererUtilsSectionTypes.MARKUP_SECTION_TYPE)) {\n return;\n }\n var renderer = _mobiledocHtmlRendererUtilsDom.createElement;\n var lowerCaseTagName = tagName.toLowerCase();\n if (this.sectionElementRenderer[lowerCaseTagName]) {\n renderer = this.sectionElementRenderer[lowerCaseTagName];\n }\n var element = renderer(tagName);\n this._renderMarkersOnElement(element, markers);\n return element;\n }\n }, {\n key: '_renderMarkersOnElement',\n value: function _renderMarkersOnElement(element, markers) {\n var elements = [element];\n var currentElement = element;\n\n for (var i = 0, l = markers.length; i < l; i++) {\n var marker = markers[i];\n\n var _marker = _slicedToArray(marker, 3);\n\n var openTypes = _marker[0];\n var closeCount = _marker[1];\n var text = _marker[2];\n\n for (var j = 0, m = openTypes.length; j < m; j++) {\n var markerType = this.markerTypes[openTypes[j]];\n\n var _markerType = _slicedToArray(markerType, 1);\n\n var tagName = _markerType[0];\n\n if ((0, _mobiledocHtmlRendererUtilsTagNames.isValidMarkerType)(tagName)) {\n var openedElement = createElementFromMarkerType(markerType);\n (0, _mobiledocHtmlRendererUtilsDom.appendChild)(currentElement, openedElement);\n elements.push(openedElement);\n currentElement = openedElement;\n } else {\n closeCount--;\n }\n }\n\n (0, _mobiledocHtmlRendererUtilsDom.appendChild)(currentElement, (0, _mobiledocHtmlRendererUtilsDom.createTextNode)(text));\n\n for (var j = 0, m = closeCount; j < m; j++) {\n elements.pop();\n currentElement = elements[elements.length - 1];\n }\n }\n }\n }, {\n key: '_defaultUnknownCardHandler',\n get: function get() {\n return function (_ref7) {\n var name = _ref7.env.name;\n\n throw new Error('Card \"' + name + '\" not found but no unknownCardHandler was registered');\n };\n }\n }]);\n\n return Renderer;\n })();\n\n exports['default'] = Renderer;\n});","define('mobiledoc-html-renderer/renderers/0-3', ['exports', 'mobiledoc-html-renderer/utils/dom', 'mobiledoc-html-renderer/cards/image', 'mobiledoc-html-renderer/utils/render-type', 'mobiledoc-html-renderer/utils/section-types', 'mobiledoc-html-renderer/utils/tag-names', 'mobiledoc-html-renderer/utils/marker-types'], function (exports, _mobiledocHtmlRendererUtilsDom, _mobiledocHtmlRendererCardsImage, _mobiledocHtmlRendererUtilsRenderType, _mobiledocHtmlRendererUtilsSectionTypes, _mobiledocHtmlRendererUtilsTagNames, _mobiledocHtmlRendererUtilsMarkerTypes) {\n 'use strict';\n\n var _slicedToArray = (function () { function sliceIterator(arr, i) { var _arr = []; var _n = true; var _d = false; var _e = undefined; try { for (var _i = arr[Symbol.iterator](), _s; !(_n = (_s = _i.next()).done); _n = true) { _arr.push(_s.value); if (i && _arr.length === i) break; } } catch (err) { _d = true; _e = err; } finally { try { if (!_n && _i['return']) _i['return'](); } finally { if (_d) throw _e; } } return _arr; } return function (arr, i) { if (Array.isArray(arr)) { return arr; } else if (Symbol.iterator in Object(arr)) { return sliceIterator(arr, i); } else { throw new TypeError('Invalid attempt to destructure non-iterable instance'); } }; })();\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n var MOBILEDOC_VERSION = '0.3.0';\n\n exports.MOBILEDOC_VERSION = MOBILEDOC_VERSION;\n /**\n * runtime HTML renderer\n * renders a mobiledoc to HTML\n *\n * input: mobiledoc\n * output: HTML\n */\n\n function createElementFromMarkerType() {\n var _ref = arguments.length <= 0 || arguments[0] === undefined ? ['', []] : arguments[0];\n\n var _ref2 = _slicedToArray(_ref, 2);\n\n var tagName = _ref2[0];\n var attributes = _ref2[1];\n\n var element = (0, _mobiledocHtmlRendererUtilsDom.createElement)(tagName);\n attributes = attributes || [];\n\n for (var i = 0, l = attributes.length; i < l; i = i + 2) {\n var propName = attributes[i],\n propValue = attributes[i + 1];\n (0, _mobiledocHtmlRendererUtilsDom.setAttribute)(element, propName, propValue);\n }\n return element;\n }\n\n function validateVersion(version) {\n if (version !== MOBILEDOC_VERSION) {\n throw new Error('Unexpected Mobiledoc version \"' + version + '\"');\n }\n }\n\n var Renderer = (function () {\n function Renderer(mobiledoc, state) {\n _classCallCheck(this, Renderer);\n\n var cards = state.cards;\n var cardOptions = state.cardOptions;\n var atoms = state.atoms;\n var unknownCardHandler = state.unknownCardHandler;\n var unknownAtomHandler = state.unknownAtomHandler;\n var sectionElementRenderer = state.sectionElementRenderer;\n var version = mobiledoc.version;\n var sections = mobiledoc.sections;\n var atomTypes = mobiledoc.atoms;\n var cardTypes = mobiledoc.cards;\n var markerTypes = mobiledoc.markups;\n\n validateVersion(version);\n\n this.root = (0, _mobiledocHtmlRendererUtilsDom.createDocumentFragment)();\n this.sections = sections;\n this.atomTypes = atomTypes;\n this.cardTypes = cardTypes;\n this.markerTypes = markerTypes;\n this.cards = cards;\n this.atoms = atoms;\n this.cardOptions = cardOptions;\n this.unknownCardHandler = unknownCardHandler || this._defaultUnknownCardHandler;\n this.unknownAtomHandler = unknownAtomHandler || this._defaultUnknownAtomHandler;\n\n this.sectionElementRenderer = {};\n if (sectionElementRenderer) {\n for (var key in sectionElementRenderer) {\n if (sectionElementRenderer.hasOwnProperty(key)) {\n this.sectionElementRenderer[key.toLowerCase()] = sectionElementRenderer[key];\n }\n }\n }\n\n this._teardownCallbacks = [];\n }\n\n _createClass(Renderer, [{\n key: 'render',\n value: function render() {\n var _this = this;\n\n this.sections.forEach(function (section) {\n var rendered = _this.renderSection(section);\n if (rendered) {\n (0, _mobiledocHtmlRendererUtilsDom.appendChild)(_this.root, rendered);\n }\n });\n\n return { result: this.root.toString(), teardown: function teardown() {\n return _this.teardown();\n } };\n }\n }, {\n key: 'teardown',\n value: function teardown() {\n for (var i = 0; i < this._teardownCallbacks.length; i++) {\n this._teardownCallbacks[i]();\n }\n }\n }, {\n key: 'renderSection',\n value: function renderSection(section) {\n var _section = _slicedToArray(section, 1);\n\n var type = _section[0];\n\n switch (type) {\n case _mobiledocHtmlRendererUtilsSectionTypes.MARKUP_SECTION_TYPE:\n return this.renderMarkupSection(section);\n case _mobiledocHtmlRendererUtilsSectionTypes.IMAGE_SECTION_TYPE:\n return this.renderImageSection(section);\n case _mobiledocHtmlRendererUtilsSectionTypes.LIST_SECTION_TYPE:\n return this.renderListSection(section);\n case _mobiledocHtmlRendererUtilsSectionTypes.CARD_SECTION_TYPE:\n return this.renderCardSection(section);\n default:\n throw new Error('Renderer cannot render type \"' + type + '\"');\n }\n }\n }, {\n key: 'renderListSection',\n value: function renderListSection(_ref3) {\n var _this2 = this;\n\n var _ref32 = _slicedToArray(_ref3, 3);\n\n var type = _ref32[0];\n var tagName = _ref32[1];\n var items = _ref32[2];\n\n if (!(0, _mobiledocHtmlRendererUtilsTagNames.isValidSectionTagName)(tagName, _mobiledocHtmlRendererUtilsSectionTypes.LIST_SECTION_TYPE)) {\n return;\n }\n var element = (0, _mobiledocHtmlRendererUtilsDom.createElement)(tagName);\n items.forEach(function (li) {\n (0, _mobiledocHtmlRendererUtilsDom.appendChild)(element, _this2.renderListItem(li));\n });\n return element;\n }\n }, {\n key: 'renderListItem',\n value: function renderListItem(markers) {\n var element = (0, _mobiledocHtmlRendererUtilsDom.createElement)('li');\n this._renderMarkersOnElement(element, markers);\n return element;\n }\n }, {\n key: 'renderImageSection',\n value: function renderImageSection(_ref4) {\n var _ref42 = _slicedToArray(_ref4, 2);\n\n var type = _ref42[0];\n var url = _ref42[1];\n\n var element = (0, _mobiledocHtmlRendererUtilsDom.createElement)('img');\n (0, _mobiledocHtmlRendererUtilsDom.setAttribute)(element, 'src', url);\n return element;\n }\n }, {\n key: 'findCard',\n value: function findCard(name) {\n for (var i = 0; i < this.cards.length; i++) {\n if (this.cards[i].name === name) {\n return this.cards[i];\n }\n }\n if (name === _mobiledocHtmlRendererCardsImage['default'].name) {\n return _mobiledocHtmlRendererCardsImage['default'];\n }\n return this._createUnknownCard(name);\n }\n }, {\n key: '_findCardByIndex',\n value: function _findCardByIndex(index) {\n var cardType = this.cardTypes[index];\n if (!cardType) {\n throw new Error('No card definition found at index ' + index);\n }\n\n var _cardType = _slicedToArray(cardType, 2);\n\n var name = _cardType[0];\n var payload = _cardType[1];\n\n var card = this.findCard(name);\n\n return {\n card: card,\n payload: payload\n };\n }\n }, {\n key: '_createUnknownCard',\n value: function _createUnknownCard(name) {\n return {\n name: name,\n type: _mobiledocHtmlRendererUtilsRenderType['default'],\n render: this.unknownCardHandler\n };\n }\n }, {\n key: 'renderCardSection',\n value: function renderCardSection(_ref5) {\n var _ref52 = _slicedToArray(_ref5, 2);\n\n var type = _ref52[0];\n var index = _ref52[1];\n\n var _findCardByIndex2 = this._findCardByIndex(index);\n\n var card = _findCardByIndex2.card;\n var payload = _findCardByIndex2.payload;\n\n var cardWrapper = this._createCardElement();\n var cardArg = this._createCardArgument(card, payload);\n var rendered = card.render(cardArg);\n\n this._validateCardRender(rendered, card.name);\n\n if (rendered) {\n (0, _mobiledocHtmlRendererUtilsDom.appendChild)(cardWrapper, rendered);\n }\n\n return cardWrapper;\n }\n }, {\n key: '_registerTeardownCallback',\n value: function _registerTeardownCallback(callback) {\n this._teardownCallbacks.push(callback);\n }\n }, {\n key: '_createCardArgument',\n value: function _createCardArgument(card) {\n var _this3 = this;\n\n var payload = arguments.length <= 1 || arguments[1] === undefined ? {} : arguments[1];\n\n var env = {\n name: card.name,\n isInEditor: false,\n onTeardown: function onTeardown(callback) {\n return _this3._registerTeardownCallback(callback);\n }\n };\n\n var options = this.cardOptions;\n\n return { env: env, options: options, payload: payload };\n }\n }, {\n key: '_validateCardRender',\n value: function _validateCardRender(rendered, cardName) {\n if (!rendered) {\n return;\n }\n\n if (typeof rendered !== 'string') {\n throw new Error('Card \"' + cardName + '\" must render ' + _mobiledocHtmlRendererUtilsRenderType['default'] + ', but result was ' + typeof rendered + '\"');\n }\n }\n }, {\n key: '_createCardElement',\n value: function _createCardElement() {\n return (0, _mobiledocHtmlRendererUtilsDom.createElement)('div');\n }\n }, {\n key: 'renderMarkupSection',\n value: function renderMarkupSection(_ref6) {\n var _ref62 = _slicedToArray(_ref6, 3);\n\n var type = _ref62[0];\n var tagName = _ref62[1];\n var markers = _ref62[2];\n\n if (!(0, _mobiledocHtmlRendererUtilsTagNames.isValidSectionTagName)(tagName, _mobiledocHtmlRendererUtilsSectionTypes.MARKUP_SECTION_TYPE)) {\n return;\n }\n var renderer = _mobiledocHtmlRendererUtilsDom.createElement;\n var lowerCaseTagName = tagName.toLowerCase();\n if (this.sectionElementRenderer[lowerCaseTagName]) {\n renderer = this.sectionElementRenderer[lowerCaseTagName];\n }\n\n var element = renderer(tagName);\n this._renderMarkersOnElement(element, markers);\n return element;\n }\n }, {\n key: 'findAtom',\n value: function findAtom(name) {\n for (var i = 0; i < this.atoms.length; i++) {\n if (this.atoms[i].name === name) {\n return this.atoms[i];\n }\n }\n return this._createUnknownAtom(name);\n }\n }, {\n key: '_createUnknownAtom',\n value: function _createUnknownAtom(name) {\n return {\n name: name,\n type: _mobiledocHtmlRendererUtilsRenderType['default'],\n render: this.unknownAtomHandler\n };\n }\n }, {\n key: '_createAtomArgument',\n value: function _createAtomArgument(atom, value, payload) {\n var _this4 = this;\n\n var env = {\n name: atom.name,\n onTeardown: function onTeardown(callback) {\n return _this4._registerTeardownCallback(callback);\n }\n };\n\n var options = this.cardOptions;\n\n return { env: env, options: options, value: value, payload: payload };\n }\n }, {\n key: '_validateAtomRender',\n value: function _validateAtomRender(rendered, atomName) {\n if (!rendered) {\n return;\n }\n\n if (typeof rendered !== 'string') {\n throw new Error('Atom \"' + atomName + '\" must render ' + _mobiledocHtmlRendererUtilsRenderType['default'] + ', but result was ' + typeof rendered + '\"');\n }\n }\n }, {\n key: '_findAtomByIndex',\n value: function _findAtomByIndex(index) {\n var atomType = this.atomTypes[index];\n if (!atomType) {\n throw new Error('No atom definition found at index ' + index);\n }\n\n var _atomType = _slicedToArray(atomType, 3);\n\n var name = _atomType[0];\n var value = _atomType[1];\n var payload = _atomType[2];\n\n var atom = this.findAtom(name);\n\n return {\n atom: atom,\n value: value,\n payload: payload\n };\n }\n }, {\n key: '_renderAtom',\n value: function _renderAtom(index) {\n var _findAtomByIndex2 = this._findAtomByIndex(index);\n\n var atom = _findAtomByIndex2.atom;\n var value = _findAtomByIndex2.value;\n var payload = _findAtomByIndex2.payload;\n\n var atomArg = this._createAtomArgument(atom, value, payload);\n var rendered = atom.render(atomArg);\n\n this._validateAtomRender(rendered, atom.name);\n\n return rendered || (0, _mobiledocHtmlRendererUtilsDom.createTextNode)('');\n }\n }, {\n key: '_renderMarkersOnElement',\n value: function _renderMarkersOnElement(element, markers) {\n var elements = [element];\n var currentElement = element;\n\n for (var i = 0, l = markers.length; i < l; i++) {\n var marker = markers[i];\n\n var _marker = _slicedToArray(marker, 4);\n\n var type = _marker[0];\n var openTypes = _marker[1];\n var closeCount = _marker[2];\n var value = _marker[3];\n\n for (var j = 0, m = openTypes.length; j < m; j++) {\n var markerType = this.markerTypes[openTypes[j]];\n\n var _markerType = _slicedToArray(markerType, 1);\n\n var tagName = _markerType[0];\n\n if ((0, _mobiledocHtmlRendererUtilsTagNames.isValidMarkerType)(tagName)) {\n var openedElement = createElementFromMarkerType(markerType);\n (0, _mobiledocHtmlRendererUtilsDom.appendChild)(currentElement, openedElement);\n elements.push(openedElement);\n currentElement = openedElement;\n } else {\n closeCount--;\n }\n }\n\n switch (type) {\n case _mobiledocHtmlRendererUtilsMarkerTypes.MARKUP_MARKER_TYPE:\n (0, _mobiledocHtmlRendererUtilsDom.appendChild)(currentElement, (0, _mobiledocHtmlRendererUtilsDom.createTextNode)(value));\n break;\n case _mobiledocHtmlRendererUtilsMarkerTypes.ATOM_MARKER_TYPE:\n (0, _mobiledocHtmlRendererUtilsDom.appendChild)(currentElement, this._renderAtom(value));\n break;\n default:\n throw new Error('Unknown markup type (' + type + ')');\n }\n\n for (var j = 0, m = closeCount; j < m; j++) {\n elements.pop();\n currentElement = elements[elements.length - 1];\n }\n }\n }\n }, {\n key: '_defaultUnknownCardHandler',\n get: function get() {\n return function (_ref7) {\n var name = _ref7.env.name;\n\n throw new Error('Card \"' + name + '\" not found but no unknownCardHandler was registered');\n };\n }\n }, {\n key: '_defaultUnknownAtomHandler',\n get: function get() {\n return function (_ref8) {\n var name = _ref8.env.name;\n\n throw new Error('Atom \"' + name + '\" not found but no unknownAtomHandler was registered');\n };\n }\n }]);\n\n return Renderer;\n })();\n\n exports['default'] = Renderer;\n});","define('mobiledoc-html-renderer/utils/dom', ['exports'], function (exports) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n exports.createElement = createElement;\n exports.appendChild = appendChild;\n exports.createTextNode = createTextNode;\n exports.setAttribute = setAttribute;\n exports.createDocumentFragment = createDocumentFragment;\n exports.normalizeTagName = normalizeTagName;\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n var VOID_TAGS = 'area base br col command embed hr img input keygen link meta param source track wbr'.split(' ');\n\n var Element = (function () {\n function Element(tagName) {\n _classCallCheck(this, Element);\n\n this.tagName = tagName.toLowerCase();\n this.isVoid = VOID_TAGS.indexOf(this.tagName) !== -1;\n this.childNodes = [];\n this.attributes = [];\n }\n\n _createClass(Element, [{\n key: 'appendChild',\n value: function appendChild(element) {\n this.childNodes.push(element);\n }\n }, {\n key: 'setAttribute',\n value: function setAttribute(propName, propValue) {\n this.attributes.push(propName, propValue);\n }\n }, {\n key: 'toString',\n value: function toString() {\n var html = '<' + this.tagName;\n\n if (this.attributes.length) {\n for (var i = 0; i < this.attributes.length; i = i + 2) {\n var propName = this.attributes[i],\n propValue = this.attributes[i + 1];\n html += ' ' + propName + '=\"' + propValue + '\"';\n }\n }\n html += '>';\n\n if (!this.isVoid) {\n for (var i = 0; i < this.childNodes.length; i++) {\n html += this.childNodes[i].toString();\n }\n html += '';\n }\n\n return html;\n }\n }]);\n\n return Element;\n })();\n\n function addHTMLSpaces(text) {\n return text.replace(/ /g, '  ');\n }\n\n var TextNode = (function () {\n function TextNode(value) {\n _classCallCheck(this, TextNode);\n\n this.value = value;\n }\n\n _createClass(TextNode, [{\n key: 'toString',\n value: function toString() {\n return addHTMLSpaces(this.value);\n }\n }]);\n\n return TextNode;\n })();\n\n function createElement(tagName) {\n return new Element(tagName);\n }\n\n function appendChild(target, child) {\n target.appendChild(child);\n }\n\n function createTextNode(text) {\n return new TextNode(text);\n }\n\n function setAttribute(element, propName, propValue) {\n element.setAttribute(propName, propValue);\n }\n\n function createDocumentFragment() {\n return createElement('div');\n }\n\n function normalizeTagName(name) {\n return name.toLowerCase();\n }\n});","define(\"mobiledoc-html-renderer/utils/marker-types\", [\"exports\"], function (exports) {\n \"use strict\";\n\n var MARKUP_MARKER_TYPE = 0;\n exports.MARKUP_MARKER_TYPE = MARKUP_MARKER_TYPE;\n var ATOM_MARKER_TYPE = 1;\n exports.ATOM_MARKER_TYPE = ATOM_MARKER_TYPE;\n});","define('mobiledoc-html-renderer/utils/render-type', ['exports'], function (exports) {\n 'use strict';\n\n exports['default'] = 'html';\n});","define(\"mobiledoc-html-renderer/utils/section-types\", [\"exports\"], function (exports) {\n \"use strict\";\n\n var MARKUP_SECTION_TYPE = 1;\n exports.MARKUP_SECTION_TYPE = MARKUP_SECTION_TYPE;\n var IMAGE_SECTION_TYPE = 2;\n exports.IMAGE_SECTION_TYPE = IMAGE_SECTION_TYPE;\n var LIST_SECTION_TYPE = 3;\n exports.LIST_SECTION_TYPE = LIST_SECTION_TYPE;\n var CARD_SECTION_TYPE = 10;\n exports.CARD_SECTION_TYPE = CARD_SECTION_TYPE;\n});","define('mobiledoc-html-renderer/utils/tag-names', ['exports', 'mobiledoc-html-renderer/utils/section-types', 'mobiledoc-html-renderer/utils/dom'], function (exports, _mobiledocHtmlRendererUtilsSectionTypes, _mobiledocHtmlRendererUtilsDom) {\n 'use strict';\n\n exports.isValidSectionTagName = isValidSectionTagName;\n exports.isValidMarkerType = isValidMarkerType;\n\n var MARKUP_SECTION_TAG_NAMES = ['p', 'h1', 'h2', 'h3', 'blockquote', 'pull-quote'].map(_mobiledocHtmlRendererUtilsDom.normalizeTagName);\n\n var LIST_SECTION_TAG_NAMES = ['ul', 'ol'].map(_mobiledocHtmlRendererUtilsDom.normalizeTagName);\n\n var MARKUP_TYPES = ['b', 'i', 'strong', 'em', 'a', 'u', 'sub', 'sup', 's'].map(_mobiledocHtmlRendererUtilsDom.normalizeTagName);\n\n function contains(array, item) {\n return array.indexOf(item) !== -1;\n }\n\n function isValidSectionTagName(tagName, sectionType) {\n tagName = (0, _mobiledocHtmlRendererUtilsDom.normalizeTagName)(tagName);\n\n switch (sectionType) {\n case _mobiledocHtmlRendererUtilsSectionTypes.MARKUP_SECTION_TYPE:\n return contains(MARKUP_SECTION_TAG_NAMES, tagName);\n case _mobiledocHtmlRendererUtilsSectionTypes.LIST_SECTION_TYPE:\n return contains(LIST_SECTION_TAG_NAMES, tagName);\n default:\n throw new Error('Cannot validate tagName for unknown section type \"' + sectionType + '\"');\n }\n }\n\n function isValidMarkerType(type) {\n type = (0, _mobiledocHtmlRendererUtilsDom.normalizeTagName)(type);\n return contains(MARKUP_TYPES, type);\n }\n});","define('mobiledoc-kit/cards/image', ['exports', 'mobiledoc-kit/utils/placeholder-image-src'], function (exports, _mobiledocKitUtilsPlaceholderImageSrc) {\n 'use strict';\n\n exports['default'] = {\n name: 'image',\n type: 'dom',\n\n render: function render(_ref) {\n var env = _ref.env;\n var options = _ref.options;\n var payload = _ref.payload;\n\n var img = document.createElement('img');\n img.src = payload.src || _mobiledocKitUtilsPlaceholderImageSrc['default'];\n return img;\n }\n };\n});","define('mobiledoc-kit/editor/edit-history', ['exports', 'mobiledoc-kit/parsers/mobiledoc', 'mobiledoc-kit/utils/fixed-queue'], function (exports, _mobiledocKitParsersMobiledoc, _mobiledocKitUtilsFixedQueue) {\n 'use strict';\n\n var _slicedToArray = (function () { function sliceIterator(arr, i) { var _arr = []; var _n = true; var _d = false; var _e = undefined; try { for (var _i = arr[Symbol.iterator](), _s; !(_n = (_s = _i.next()).done); _n = true) { _arr.push(_s.value); if (i && _arr.length === i) break; } } catch (err) { _d = true; _e = err; } finally { try { if (!_n && _i['return']) _i['return'](); } finally { if (_d) throw _e; } } return _arr; } return function (arr, i) { if (Array.isArray(arr)) { return arr; } else if (Symbol.iterator in Object(arr)) { return sliceIterator(arr, i); } else { throw new TypeError('Invalid attempt to destructure non-iterable instance'); } }; })();\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n function findLeafSectionAtIndex(post, index) {\n var section = undefined;\n post.walkAllLeafSections(function (_section, _index) {\n if (index === _index) {\n section = _section;\n }\n });\n return section;\n }\n\n var Snapshot = (function () {\n function Snapshot(editor) {\n _classCallCheck(this, Snapshot);\n\n this.mobiledoc = editor.serialize();\n this.editor = editor;\n\n this.snapshotRange();\n }\n\n _createClass(Snapshot, [{\n key: 'snapshotRange',\n value: function snapshotRange() {\n var _editor = this.editor;\n var range = _editor.range;\n var cursor = _editor.cursor;\n\n if (cursor.hasCursor() && !range.isBlank) {\n var head = range.head;\n var tail = range.tail;\n\n this.range = {\n head: [head.leafSectionIndex, head.offset],\n tail: [tail.leafSectionIndex, tail.offset]\n };\n }\n }\n }, {\n key: 'getRange',\n value: function getRange(post) {\n if (this.range) {\n var _range = this.range;\n var head = _range.head;\n var tail = _range.tail;\n var _head = head;\n\n var _head2 = _slicedToArray(_head, 2);\n\n var headLeafSectionIndex = _head2[0];\n var headOffset = _head2[1];\n var _tail = tail;\n\n var _tail2 = _slicedToArray(_tail, 2);\n\n var tailLeafSectionIndex = _tail2[0];\n var tailOffset = _tail2[1];\n\n var headSection = findLeafSectionAtIndex(post, headLeafSectionIndex);\n var tailSection = findLeafSectionAtIndex(post, tailLeafSectionIndex);\n\n head = headSection.toPosition(headOffset);\n tail = tailSection.toPosition(tailOffset);\n\n return head.toRange(tail);\n }\n }\n }]);\n\n return Snapshot;\n })();\n\n exports.Snapshot = Snapshot;\n\n var EditHistory = (function () {\n function EditHistory(editor, queueLength) {\n _classCallCheck(this, EditHistory);\n\n this.editor = editor;\n this._undoStack = new _mobiledocKitUtilsFixedQueue['default'](queueLength);\n this._redoStack = new _mobiledocKitUtilsFixedQueue['default'](queueLength);\n\n this._pendingSnapshot = null;\n }\n\n _createClass(EditHistory, [{\n key: 'snapshot',\n value: function snapshot() {\n // update the current snapshot with the range read from DOM\n if (this._pendingSnapshot) {\n this._pendingSnapshot.snapshotRange();\n }\n }\n }, {\n key: 'storeSnapshot',\n value: function storeSnapshot() {\n // store pending snapshot\n if (this._pendingSnapshot) {\n this._undoStack.push(this._pendingSnapshot);\n this._redoStack.clear();\n }\n\n // take new pending snapshot to store next time `storeSnapshot` is called\n this._pendingSnapshot = new Snapshot(this.editor);\n }\n }, {\n key: 'stepBackward',\n value: function stepBackward(postEditor) {\n // Throw away the pending snapshot\n this._pendingSnapshot = null;\n\n var snapshot = this._undoStack.pop();\n if (snapshot) {\n this._redoStack.push(new Snapshot(this.editor));\n this._restoreFromSnapshot(snapshot, postEditor);\n }\n }\n }, {\n key: 'stepForward',\n value: function stepForward(postEditor) {\n var snapshot = this._redoStack.pop();\n if (snapshot) {\n this._undoStack.push(new Snapshot(this.editor));\n this._restoreFromSnapshot(snapshot, postEditor);\n }\n postEditor.cancelSnapshot();\n }\n }, {\n key: '_restoreFromSnapshot',\n value: function _restoreFromSnapshot(snapshot, postEditor) {\n var mobiledoc = snapshot.mobiledoc;\n var editor = this.editor;\n var builder = editor.builder;\n var post = editor.post;\n\n var restoredPost = _mobiledocKitParsersMobiledoc['default'].parse(builder, mobiledoc);\n\n postEditor.removeAllSections();\n postEditor.migrateSectionsFromPost(restoredPost);\n\n // resurrect snapshotted range if it exists\n var newRange = snapshot.getRange(post);\n if (newRange) {\n postEditor.setRange(newRange);\n }\n }\n }]);\n\n return EditHistory;\n })();\n\n exports['default'] = EditHistory;\n});","define('mobiledoc-kit/editor/edit-state', ['exports', 'mobiledoc-kit/utils/array-utils', 'mobiledoc-kit/utils/cursor/range'], function (exports, _mobiledocKitUtilsArrayUtils, _mobiledocKitUtilsCursorRange) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n /**\n * Used by {@link Editor} to manage its current state (cursor, active markups\n * and active sections).\n * @private\n */\n\n var EditState = (function () {\n function EditState(editor) {\n _classCallCheck(this, EditState);\n\n this.editor = editor;\n\n var defaultState = {\n range: _mobiledocKitUtilsCursorRange['default'].blankRange(),\n activeMarkups: [],\n activeSections: [],\n activeSectionTagNames: []\n };\n\n this.prevState = this.state = defaultState;\n }\n\n _createClass(EditState, [{\n key: 'updateRange',\n value: function updateRange(newRange) {\n this.prevState = this.state;\n this.state = this._readState(newRange);\n }\n }, {\n key: 'destroy',\n value: function destroy() {\n this.editor = null;\n this.prevState = this.state = null;\n }\n\n /**\n * @return {Boolean}\n */\n }, {\n key: 'rangeDidChange',\n value: function rangeDidChange() {\n var range = this.state.range;\n var prevRange = this.prevState.range;\n\n return !prevRange.isEqual(range);\n }\n\n /**\n * @return {Boolean} Whether the input mode (active markups or active section tag names)\n * has changed.\n */\n }, {\n key: 'inputModeDidChange',\n value: function inputModeDidChange() {\n var state = this.state;\n var prevState = this.prevState;\n\n return !(0, _mobiledocKitUtilsArrayUtils.isArrayEqual)(state.activeMarkups, prevState.activeMarkups) || !(0, _mobiledocKitUtilsArrayUtils.isArrayEqual)(state.activeSectionTagNames, prevState.activeSectionTagNames);\n }\n\n /**\n * @return {Range}\n */\n }, {\n key: 'toggleMarkupState',\n\n /**\n * Update the editor's markup state. This is used when, e.g.,\n * a user types meta+B when the editor has a cursor but no selected text;\n * in this case the editor needs to track that it has an active \"b\" markup\n * and apply it to the next text the user types.\n */\n value: function toggleMarkupState(markup) {\n if ((0, _mobiledocKitUtilsArrayUtils.contains)(this.activeMarkups, markup)) {\n this._removeActiveMarkup(markup);\n } else {\n this._addActiveMarkup(markup);\n }\n }\n }, {\n key: '_readState',\n value: function _readState(range) {\n var state = {\n range: range,\n activeMarkups: this._readActiveMarkups(range),\n activeSections: this._readActiveSections(range)\n };\n // Section objects are 'live', so to check that they changed, we\n // need to map their tagNames now (and compare to mapped tagNames later).\n // In addition, to catch changes from ul -> ol, we keep track of the\n // un-nested tag names (otherwise we'd only see li -> li change)\n state.activeSectionTagNames = state.activeSections.map(function (s) {\n return s.isNested ? s.parent.tagName : s.tagName;\n });\n return state;\n }\n }, {\n key: '_readActiveSections',\n value: function _readActiveSections(range) {\n var head = range.head;\n var tail = range.tail;\n var post = this.editor.post;\n\n if (range.isBlank) {\n return [];\n } else {\n return post.sections.readRange(head.section, tail.section);\n }\n }\n }, {\n key: '_readActiveMarkups',\n value: function _readActiveMarkups(range) {\n var post = this.editor.post;\n\n return post.markupsInRange(range);\n }\n }, {\n key: '_removeActiveMarkup',\n value: function _removeActiveMarkup(markup) {\n var index = this.state.activeMarkups.indexOf(markup);\n this.state.activeMarkups.splice(index, 1);\n }\n }, {\n key: '_addActiveMarkup',\n value: function _addActiveMarkup(markup) {\n this.state.activeMarkups.push(markup);\n }\n }, {\n key: 'range',\n get: function get() {\n return this.state.range;\n }\n\n /**\n * @return {Section[]}\n */\n }, {\n key: 'activeSections',\n get: function get() {\n return this.state.activeSections;\n }\n\n /**\n * @return {Markup[]}\n */\n }, {\n key: 'activeMarkups',\n get: function get() {\n return this.state.activeMarkups;\n }\n }]);\n\n return EditState;\n })();\n\n exports['default'] = EditState;\n});","define('mobiledoc-kit/editor/editor', ['exports', 'mobiledoc-kit/views/tooltip', 'mobiledoc-kit/editor/post', 'mobiledoc-kit/cards/image', 'mobiledoc-kit/utils/key', 'mobiledoc-kit/parsers/mobiledoc', 'mobiledoc-kit/parsers/html', 'mobiledoc-kit/parsers/dom', 'mobiledoc-kit/renderers/editor-dom', 'mobiledoc-kit/models/render-tree', 'mobiledoc-kit/renderers/mobiledoc', 'mobiledoc-kit/utils/merge', 'mobiledoc-kit/utils/dom-utils', 'mobiledoc-kit/utils/array-utils', 'mobiledoc-kit/utils/element-utils', 'mobiledoc-kit/utils/cursor', 'mobiledoc-kit/utils/cursor/range', 'mobiledoc-kit/utils/cursor/position', 'mobiledoc-kit/models/post-node-builder', 'mobiledoc-kit/editor/text-input-handlers', 'mobiledoc-kit/editor/key-commands', 'mobiledoc-kit/models/card', 'mobiledoc-kit/utils/assert', 'mobiledoc-kit/editor/mutation-handler', 'mobiledoc-kit/editor/edit-history', 'mobiledoc-kit/editor/event-manager', 'mobiledoc-kit/editor/edit-state', 'mobiledoc-html-renderer', 'mobiledoc-text-renderer', 'mobiledoc-kit/models/lifecycle-callbacks', 'mobiledoc-kit/utils/log-manager', 'mobiledoc-kit/utils/to-range', 'mobiledoc-kit/utils/mobiledoc-error'], function (exports, _mobiledocKitViewsTooltip, _mobiledocKitEditorPost, _mobiledocKitCardsImage, _mobiledocKitUtilsKey, _mobiledocKitParsersMobiledoc, _mobiledocKitParsersHtml, _mobiledocKitParsersDom, _mobiledocKitRenderersEditorDom, _mobiledocKitModelsRenderTree, _mobiledocKitRenderersMobiledoc, _mobiledocKitUtilsMerge, _mobiledocKitUtilsDomUtils, _mobiledocKitUtilsArrayUtils, _mobiledocKitUtilsElementUtils, _mobiledocKitUtilsCursor, _mobiledocKitUtilsCursorRange, _mobiledocKitUtilsCursorPosition, _mobiledocKitModelsPostNodeBuilder, _mobiledocKitEditorTextInputHandlers, _mobiledocKitEditorKeyCommands, _mobiledocKitModelsCard, _mobiledocKitUtilsAssert, _mobiledocKitEditorMutationHandler, _mobiledocKitEditorEditHistory, _mobiledocKitEditorEventManager, _mobiledocKitEditorEditState, _mobiledocHtmlRenderer, _mobiledocTextRenderer, _mobiledocKitModelsLifecycleCallbacks, _mobiledocKitUtilsLogManager, _mobiledocKitUtilsToRange, _mobiledocKitUtilsMobiledocError) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n // This export may later be deprecated, but re-export it from the renderer here\n // for consumers that may depend on it.\n Object.defineProperty(exports, 'EDITOR_ELEMENT_CLASS_NAME', {\n enumerable: true,\n get: function get() {\n return _mobiledocKitRenderersEditorDom.EDITOR_ELEMENT_CLASS_NAME;\n }\n });\n\n var defaults = {\n placeholder: 'Write here...',\n spellcheck: true,\n autofocus: true,\n undoDepth: 5,\n cards: [],\n atoms: [],\n cardOptions: {},\n unknownCardHandler: function unknownCardHandler(_ref) {\n var env = _ref.env;\n\n throw new _mobiledocKitUtilsMobiledocError['default']('Unknown card encountered: ' + env.name);\n },\n unknownAtomHandler: function unknownAtomHandler(_ref2) {\n var env = _ref2.env;\n\n throw new _mobiledocKitUtilsMobiledocError['default']('Unknown atom encountered: ' + env.name);\n },\n mobiledoc: null,\n html: null\n };\n\n var CALLBACK_QUEUES = {\n DID_UPDATE: 'didUpdate',\n WILL_RENDER: 'willRender',\n DID_RENDER: 'didRender',\n WILL_DELETE: 'willDelete',\n DID_DELETE: 'didDelete',\n WILL_HANDLE_NEWLINE: 'willHandleNewline',\n CURSOR_DID_CHANGE: 'cursorDidChange',\n DID_REPARSE: 'didReparse',\n POST_DID_CHANGE: 'postDidChange',\n INPUT_MODE_DID_CHANGE: 'inputModeDidChange'\n };\n\n /**\n * The Editor is a core component of mobiledoc-kit. After instantiating\n * an editor, use {@link Editor#render} to display the editor on the web page.\n *\n * An editor uses a {@link Post} internally to represent the displayed document.\n * The post can be serialized as mobiledoc using {@link Editor#serialize}. Mobiledoc\n * is the transportable \"over-the-wire\" format (JSON) that is suited for persisting\n * and sharing between editors and renderers (for display, e.g.), whereas the Post\n * model is better suited for programmatic editing.\n *\n * The editor will call registered callbacks for certain state changes. These are:\n * * {@link Editor#cursorDidChange} -- The cursor position or selection changed.\n * * {@link Editor#postDidChange} -- The contents of the post changed due to user input or\n * programmatic editing. This hook can be used with {@link Editor#serialize}\n * to auto-save a post as it is being edited.\n * * {@link Editor#inputModeDidChange} -- The active section(s) or markup(s) at the current cursor\n * position or selection have changed. This hook can be used with\n * {@link Editor#activeMarkups} and {@link Editor#activeSections} to implement\n * a custom toolbar.\n * * {@link Editor#onTextInput} -- Register callbacks when the user enters text\n * that matches a given string or regex.\n */\n\n var Editor = (function () {\n /**\n * @param {Object} [options]\n * @param {Object} [options.mobiledoc] The mobiledoc to load into the editor.\n * Supersedes `options.html`.\n * @param {String|DOM} [options.html] The html (as a string or DOM fragment)\n * to parse and load into the editor.\n * Will be ignored if `options.mobiledoc` is also passed.\n * @param {Array} [options.parserPlugins=[]]\n * @param {Array} [options.cards=[]] The cards that the editor may render.\n * @param {Array} [options.atoms=[]] The atoms that the editor may render.\n * @param {Function} [options.unknownCardHandler] Invoked by the editor's renderer\n * whenever it encounters an unknown card.\n * @param {Function} [options.unknownAtomHandler] Invoked by the editor's renderer\n * whenever it encounters an unknown atom.\n * @param {String} [options.placeholder] Default text to show before user starts typing.\n * @param {Boolean} [options.spellcheck=true] Whether to enable spellcheck\n * @param {Boolean} [options.autofocus=true] Whether to focus the editor when it is first rendered.\n * @param {number} [options.undoDepth=5] How many undo levels will be available.\n * Set to 0 to disable undo/redo functionality.\n * @return {Editor}\n * @public\n */\n\n function Editor() {\n var _this = this;\n\n var options = arguments.length <= 0 || arguments[0] === undefined ? {} : arguments[0];\n\n _classCallCheck(this, Editor);\n\n (0, _mobiledocKitUtilsAssert['default'])('editor create accepts an options object. For legacy usage passing an element for the first argument, consider the `html` option for loading DOM or HTML posts. For other cases call `editor.render(domNode)` after editor creation', options && !options.nodeType);\n this._views = [];\n this.isEditable = null;\n this._parserPlugins = options.parserPlugins || [];\n\n // FIXME: This should merge onto this.options\n (0, _mobiledocKitUtilsMerge.mergeWithOptions)(this, defaults, options);\n this.cards.push(_mobiledocKitCardsImage['default']);\n\n _mobiledocKitEditorKeyCommands.DEFAULT_KEY_COMMANDS.forEach(function (kc) {\n return _this.registerKeyCommand(kc);\n });\n\n this._logManager = new _mobiledocKitUtilsLogManager['default']();\n this._parser = new _mobiledocKitParsersDom['default'](this.builder);\n var cards = this.cards;\n var atoms = this.atoms;\n var unknownCardHandler = this.unknownCardHandler;\n var unknownAtomHandler = this.unknownAtomHandler;\n var cardOptions = this.cardOptions;\n\n this._renderer = new _mobiledocKitRenderersEditorDom['default'](this, cards, atoms, unknownCardHandler, unknownAtomHandler, cardOptions);\n\n this.post = this.loadPost();\n this._renderTree = new _mobiledocKitModelsRenderTree['default'](this.post);\n\n this._editHistory = new _mobiledocKitEditorEditHistory['default'](this, this.undoDepth);\n this._eventManager = new _mobiledocKitEditorEventManager['default'](this);\n this._mutationHandler = new _mobiledocKitEditorMutationHandler['default'](this);\n this._editState = new _mobiledocKitEditorEditState['default'](this);\n this._callbacks = new _mobiledocKitModelsLifecycleCallbacks['default']((0, _mobiledocKitUtilsArrayUtils.values)(CALLBACK_QUEUES));\n\n _mobiledocKitEditorTextInputHandlers.DEFAULT_TEXT_INPUT_HANDLERS.forEach(function (handler) {\n return _this.onTextInput(handler);\n });\n\n this.hasRendered = false;\n }\n\n /**\n * Turns on verbose logging for the editor.\n * @param {Array} [logTypes=[]] If present, only the given log types will be logged.\n * @public\n */\n\n _createClass(Editor, [{\n key: 'enableLogging',\n value: function enableLogging() {\n var logTypes = arguments.length <= 0 || arguments[0] === undefined ? [] : arguments[0];\n\n if (logTypes.length === 0) {\n this._logManager.enableAll();\n } else {\n this._logManager.enableTypes(logTypes);\n }\n }\n\n /**\n * Disable all logging\n * @public\n */\n }, {\n key: 'disableLogging',\n value: function disableLogging() {\n this._logManager.disable();\n }\n\n /**\n * @private\n */\n }, {\n key: 'loggerFor',\n value: function loggerFor(type) {\n return this._logManager['for'](type);\n }\n\n /**\n * The editor's instance of a post node builder.\n * @type {PostNodeBuilder}\n */\n }, {\n key: 'loadPost',\n value: function loadPost() {\n var mobiledoc = this.mobiledoc;\n var html = this.html;\n\n if (mobiledoc) {\n return _mobiledocKitParsersMobiledoc['default'].parse(this.builder, mobiledoc);\n } else if (html) {\n if (typeof html === 'string') {\n var options = { plugins: this._parserPlugins };\n return new _mobiledocKitParsersHtml['default'](this.builder, options).parse(this.html);\n } else {\n var dom = html;\n return this._parser.parse(dom);\n }\n } else {\n return this.builder.createPost();\n }\n }\n }, {\n key: 'rerender',\n value: function rerender() {\n var _this2 = this;\n\n var postRenderNode = this.post.renderNode;\n\n // if we haven't rendered this post's renderNode before, mark it dirty\n if (!postRenderNode.element) {\n (0, _mobiledocKitUtilsAssert['default'])('Must call `render` before `rerender` can be called', this.hasRendered);\n postRenderNode.element = this.element;\n postRenderNode.markDirty();\n }\n\n this.runCallbacks(CALLBACK_QUEUES.WILL_RENDER);\n this._mutationHandler.suspendObservation(function () {\n _this2._renderer.render(_this2._renderTree);\n });\n this.runCallbacks(CALLBACK_QUEUES.DID_RENDER);\n }\n\n /**\n * @param {Element} element The DOM element to render into.\n * Its contents will be replaced by the editor's rendered post.\n * @public\n */\n }, {\n key: 'render',\n value: function render(element) {\n (0, _mobiledocKitUtilsAssert['default'])('Cannot render an editor twice. Use `rerender` to update the ' + 'rendering of an existing editor instance.', !this.hasRendered);\n\n element.spellcheck = this.spellcheck;\n\n (0, _mobiledocKitUtilsDomUtils.clearChildNodes)(element);\n\n this.element = element;\n\n if (this.isEditable === null) {\n this.enableEditing();\n }\n\n this._addTooltip();\n\n // A call to `run` will trigger the didUpdatePostCallbacks hooks with a\n // postEditor.\n this.run(function () {});\n\n // Only set `hasRendered` to true after calling `run` to ensure that\n // no cursorDidChange or other callbacks get fired before the editor is\n // done rendering\n this.hasRendered = true;\n this.rerender();\n\n this._mutationHandler.init();\n this._eventManager.init();\n\n if (this.autofocus) {\n this.selectRange(this.post.headPosition());\n }\n }\n }, {\n key: '_addTooltip',\n value: function _addTooltip() {\n this.addView(new _mobiledocKitViewsTooltip['default']({\n rootElement: this.element,\n showForTag: 'a'\n }));\n }\n }, {\n key: 'registerKeyCommand',\n\n /**\n * @param {Object} keyCommand The key command to register. It must specify a\n * modifier key (meta, ctrl, etc), a string representing the ascii key, and\n * a `run` method that will be passed the editor instance when the key command\n * is invoked\n * @public\n */\n value: function registerKeyCommand(rawKeyCommand) {\n var keyCommand = (0, _mobiledocKitEditorKeyCommands.buildKeyCommand)(rawKeyCommand);\n (0, _mobiledocKitUtilsAssert['default'])('Key Command is not valid', (0, _mobiledocKitEditorKeyCommands.validateKeyCommand)(keyCommand));\n this.keyCommands.unshift(keyCommand);\n }\n\n /**\n * Convenience for {@link PostEditor#deleteAtPosition}. Deletes and puts the\n * cursor in the new position.\n * @public\n */\n }, {\n key: 'deleteAtPosition',\n value: function deleteAtPosition(position, direction, _ref3) {\n var unit = _ref3.unit;\n\n this.run(function (postEditor) {\n var nextPosition = postEditor.deleteAtPosition(position, direction, { unit: unit });\n postEditor.setRange(nextPosition);\n });\n }\n\n /**\n * Convenience for {@link PostEditor#deleteRange}. Deletes and puts the\n * cursor in the new position.\n * @param {Range} range\n * @public\n */\n }, {\n key: 'deleteRange',\n value: function deleteRange(range) {\n this.run(function (postEditor) {\n var nextPosition = postEditor.deleteRange(range);\n postEditor.setRange(nextPosition);\n });\n }\n\n /**\n * @private\n */\n }, {\n key: 'performDelete',\n value: function performDelete() {\n var _ref4 = arguments.length <= 0 || arguments[0] === undefined ? { direction: _mobiledocKitUtilsKey.DIRECTION.BACKWARD, unit: 'char' } : arguments[0];\n\n var direction = _ref4.direction;\n var unit = _ref4.unit;\n var range = this.range;\n\n this.runCallbacks(CALLBACK_QUEUES.WILL_DELETE, [range, direction, unit]);\n if (range.isCollapsed) {\n this.deleteAtPosition(range.head, direction, { unit: unit });\n } else {\n this.deleteRange(range);\n }\n this.runCallbacks(CALLBACK_QUEUES.DID_DELETE, [range, direction, unit]);\n }\n }, {\n key: 'handleNewline',\n value: function handleNewline(event) {\n var _this3 = this;\n\n if (!this.hasCursor()) {\n return;\n }\n\n event.preventDefault();\n\n var range = this.range;\n\n this.run(function (postEditor) {\n var cursorSection = undefined;\n if (!range.isCollapsed) {\n var nextPosition = postEditor.deleteRange(range);\n cursorSection = nextPosition.section;\n if (cursorSection && cursorSection.isBlank) {\n postEditor.setRange(cursorSection.headPosition());\n return;\n }\n }\n\n // Above logic might delete redundant range, so callback must run after it.\n var defaultPrevented = false;\n var event = { preventDefault: function preventDefault() {\n defaultPrevented = true;\n } };\n _this3.runCallbacks(CALLBACK_QUEUES.WILL_HANDLE_NEWLINE, [event]);\n if (defaultPrevented) {\n return;\n }\n\n cursorSection = postEditor.splitSection(range.head)[1];\n postEditor.setRange(cursorSection.headPosition());\n });\n }\n\n /**\n * Notify the editor that the post did change, and run associated\n * callbacks.\n * @private\n */\n }, {\n key: '_postDidChange',\n value: function _postDidChange() {\n this.runCallbacks(CALLBACK_QUEUES.POST_DID_CHANGE);\n }\n\n /**\n * Selects the given range or position. If given a collapsed range or a position, this positions the cursor\n * at the range's position. Otherwise a selection is created in the editor\n * surface encompassing the range.\n * @param {Range|Position} range\n */\n }, {\n key: 'selectRange',\n value: function selectRange(range) {\n range = (0, _mobiledocKitUtilsToRange['default'])(range);\n\n this.cursor.selectRange(range);\n this.range = range;\n }\n }, {\n key: '_readRangeFromDOM',\n value: function _readRangeFromDOM() {\n this.range = this.cursor.offsets;\n }\n }, {\n key: 'setPlaceholder',\n value: function setPlaceholder(placeholder) {\n (0, _mobiledocKitUtilsElementUtils.setData)(this.element, 'placeholder', placeholder);\n }\n }, {\n key: '_reparsePost',\n value: function _reparsePost() {\n var post = this._parser.parse(this.element);\n this.run(function (postEditor) {\n postEditor.removeAllSections();\n postEditor.migrateSectionsFromPost(post);\n postEditor.setRange(_mobiledocKitUtilsCursorRange['default'].blankRange());\n });\n\n this.runCallbacks(CALLBACK_QUEUES.DID_REPARSE);\n this._postDidChange();\n }\n }, {\n key: '_reparseSections',\n value: function _reparseSections() {\n var _this4 = this;\n\n var sections = arguments.length <= 0 || arguments[0] === undefined ? [] : arguments[0];\n\n var currentRange = undefined;\n sections.forEach(function (section) {\n _this4._parser.reparseSection(section, _this4._renderTree);\n });\n this._removeDetachedSections();\n\n if (this._renderTree.isDirty) {\n currentRange = this.range;\n }\n\n // force the current snapshot's range to remain the same rather than\n // rereading it from DOM after the new character is applied and the browser\n // updates the cursor position\n var range = this._editHistory._pendingSnapshot.range;\n this.run(function () {\n _this4._editHistory._pendingSnapshot.range = range;\n });\n this.rerender();\n if (currentRange) {\n this.selectRange(currentRange);\n }\n\n this.runCallbacks(CALLBACK_QUEUES.DID_REPARSE);\n this._postDidChange();\n }\n\n // FIXME this should be able to be removed now -- if any sections are detached,\n // it's due to a bug in the code.\n }, {\n key: '_removeDetachedSections',\n value: function _removeDetachedSections() {\n (0, _mobiledocKitUtilsArrayUtils.forEach)((0, _mobiledocKitUtilsArrayUtils.filter)(this.post.sections, function (s) {\n return !s.renderNode.isAttached();\n }), function (s) {\n return s.renderNode.scheduleForRemoval();\n });\n }\n\n /**\n * The sections from the cursor's selection start to the selection end\n * @type {Section[]}\n */\n }, {\n key: 'detectMarkupInRange',\n value: function detectMarkupInRange(range, markupTagName) {\n var markups = this.post.markupsInRange(range);\n return (0, _mobiledocKitUtilsArrayUtils.detect)(markups, function (markup) {\n return markup.hasTag(markupTagName);\n });\n }\n\n /**\n * @type {Markup[]}\n * @public\n */\n }, {\n key: 'hasActiveMarkup',\n\n /**\n * @param {Markup|String} markup A markup instance, or a string (e.g. \"b\")\n * @return {boolean}\n */\n value: function hasActiveMarkup(markup) {\n var matchesFn = undefined;\n if (typeof markup === 'string') {\n (function () {\n var tagName = (0, _mobiledocKitUtilsDomUtils.normalizeTagName)(markup);\n matchesFn = function (m) {\n return m.tagName === tagName;\n };\n })();\n } else {\n matchesFn = function (m) {\n return m === markup;\n };\n }\n\n return !!(0, _mobiledocKitUtilsArrayUtils.detect)(this.activeMarkups, matchesFn);\n }\n\n /**\n * @param {String} version The mobiledoc version to serialize to.\n * @return {Mobiledoc} Serialized mobiledoc\n * @public\n */\n }, {\n key: 'serialize',\n value: function serialize() {\n var version = arguments.length <= 0 || arguments[0] === undefined ? _mobiledocKitRenderersMobiledoc.MOBILEDOC_VERSION : arguments[0];\n\n return this.serializePost(this.post, 'mobiledoc', { version: version });\n }\n\n /**\n * Serialize the editor's post to the requested format.\n * Note that only mobiledoc format is lossless. If cards or atoms are present\n * in the post, the html and text formats will omit them in output because\n * the editor does not have access to the html and text versions of the\n * cards/atoms.\n * @param {string} format The format to serialize ('mobiledoc', 'text', 'html')\n * @return {Object|String} The editor's post, serialized to {format}\n * @public\n */\n }, {\n key: 'serializeTo',\n value: function serializeTo(format) {\n var post = this.post;\n return this.serializePost(post, format);\n }\n\n /**\n * @param {Post}\n * @param {String} format Same as {serializeTo}\n * @param {Object} [options]\n * @param {String} [options.version=MOBILEDOC_VERSION] version to serialize to\n * @return {Object|String}\n * @private\n */\n }, {\n key: 'serializePost',\n value: function serializePost(post, format) {\n var options = arguments.length <= 2 || arguments[2] === undefined ? {} : arguments[2];\n\n var validFormats = ['mobiledoc', 'html', 'text'];\n (0, _mobiledocKitUtilsAssert['default'])('Unrecognized serialization format ' + format, (0, _mobiledocKitUtilsArrayUtils.contains)(validFormats, format));\n\n if (format === 'mobiledoc') {\n var version = options.version || _mobiledocKitRenderersMobiledoc.MOBILEDOC_VERSION;\n return _mobiledocKitRenderersMobiledoc['default'].render(post, version);\n } else {\n var rendered = undefined;\n var mobiledoc = this.serializePost(post, 'mobiledoc');\n var unknownCardHandler = function unknownCardHandler() {};\n var unknownAtomHandler = function unknownAtomHandler() {};\n var rendererOptions = { unknownCardHandler: unknownCardHandler, unknownAtomHandler: unknownAtomHandler };\n\n switch (format) {\n case 'html':\n rendered = new _mobiledocHtmlRenderer['default'](rendererOptions).render(mobiledoc);\n return rendered.result;\n case 'text':\n rendered = new _mobiledocTextRenderer['default'](rendererOptions).render(mobiledoc);\n return rendered.result;\n }\n }\n }\n }, {\n key: 'addView',\n value: function addView(view) {\n this._views.push(view);\n }\n }, {\n key: 'removeAllViews',\n value: function removeAllViews() {\n this._views.forEach(function (v) {\n return v.destroy();\n });\n this._views = [];\n }\n\n /**\n * Whether the editor has a cursor (or a selected range).\n * It is possible for the editor to be focused but not have a selection.\n * In this case, key events will fire but the editor will not be able to\n * determine a cursor position, so they will be ignored.\n * @return {boolean}\n * @public\n */\n }, {\n key: 'hasCursor',\n value: function hasCursor() {\n return this.cursor.hasCursor();\n }\n\n /**\n * Tears down the editor's attached event listeners and views.\n * @public\n */\n }, {\n key: 'destroy',\n value: function destroy() {\n this.isDestroyed = true;\n if (this._hasSelection()) {\n this.cursor.clearSelection();\n }\n if (this._hasFocus()) {\n this.element.blur(); // FIXME This doesn't blur the element on IE11\n }\n this._mutationHandler.destroy();\n this._eventManager.destroy();\n this.removeAllViews();\n this._renderer.destroy();\n this._editState.destroy();\n }\n\n /**\n * Keep the user from directly editing the post using the keyboard and mouse.\n * Modification via the programmatic API is still permitted.\n * @see Editor#enableEditing\n * @public\n */\n }, {\n key: 'disableEditing',\n value: function disableEditing() {\n if (this.isEditable === false) {\n return;\n }\n\n this.isEditable = false;\n if (this.hasRendered) {\n this.element.setAttribute('contentEditable', false);\n this.setPlaceholder('');\n this.selectRange(_mobiledocKitUtilsCursorRange['default'].blankRange());\n }\n }\n\n /**\n * Allow the user to directly interact with editing a post via keyboard and mouse input.\n * Editor instances are editable by default. Use this method to re-enable\n * editing after disabling it.\n * @see Editor#disableEditing\n * @public\n */\n }, {\n key: 'enableEditing',\n value: function enableEditing() {\n this.isEditable = true;\n if (this.element) {\n this.element.setAttribute('contentEditable', true);\n this.setPlaceholder(this.placeholder);\n }\n }\n\n /**\n * Change a cardSection into edit mode\n * If called before the card has been rendered, it will be marked so that\n * it is rendered in edit mode when it gets rendered.\n * @param {CardSection} cardSection\n * @public\n */\n }, {\n key: 'editCard',\n value: function editCard(cardSection) {\n this._setCardMode(cardSection, _mobiledocKitModelsCard.CARD_MODES.EDIT);\n }\n\n /**\n * Change a cardSection into display mode\n * If called before the card has been rendered, it will be marked so that\n * it is rendered in display mode when it gets rendered.\n * @param {CardSection} cardSection\n * @return undefined\n * @public\n */\n }, {\n key: 'displayCard',\n value: function displayCard(cardSection) {\n this._setCardMode(cardSection, _mobiledocKitModelsCard.CARD_MODES.DISPLAY);\n }\n\n /**\n * Run a new post editing session. Yields a block with a new {@link PostEditor}\n * instance. This instance can be used to interact with the post abstract.\n * Rendering will be deferred until after the callback is completed.\n *\n * Usage:\n * ```\n * let markerRange = this.range;\n * editor.run((postEditor) => {\n * postEditor.deleteRange(markerRange);\n * // editing surface not updated yet\n * postEditor.schedule(() => {\n * console.log('logs during rerender flush');\n * });\n * // logging not yet flushed\n * });\n * // editing surface now updated.\n * // logging now flushed\n * ```\n *\n * @param {Function} callback Called with an instance of\n * {@link PostEditor} as its argument.\n * @return {Mixed} The return value of `callback`.\n * @public\n */\n }, {\n key: 'run',\n value: function run(callback) {\n var postEditor = new _mobiledocKitEditorPost['default'](this);\n postEditor.begin();\n this._editHistory.snapshot();\n var result = callback(postEditor);\n this.runCallbacks(CALLBACK_QUEUES.DID_UPDATE, [postEditor]);\n postEditor.complete();\n this._readRangeFromDOM();\n\n if (postEditor._shouldCancelSnapshot) {\n this._editHistory._pendingSnapshot = null;\n }\n this._editHistory.storeSnapshot();\n\n return result;\n }\n\n /**\n * @param {Function} callback Called with `postEditor` as its argument.\n * @public\n */\n }, {\n key: 'didUpdatePost',\n value: function didUpdatePost(callback) {\n this.addCallback(CALLBACK_QUEUES.DID_UPDATE, callback);\n }\n\n /**\n * @param {Function} callback Called when the post has changed, either via\n * user input or programmatically. Use with {@link Editor#serialize} to\n * retrieve the post in portable mobiledoc format.\n */\n }, {\n key: 'postDidChange',\n value: function postDidChange(callback) {\n this.addCallback(CALLBACK_QUEUES.POST_DID_CHANGE, callback);\n }\n\n /**\n * Register a handler that will be invoked by the editor after the user enters\n * matching text.\n * @param {Object} inputHandler\n * @param {String} inputHandler.name Required. Used by identifying handlers.\n * @param {String} [inputHandler.text] Required if `match` is not provided\n * @param {RegExp} [inputHandler.match] Required if `text` is not provided\n * @param {Function} inputHandler.run This callback is invoked with the {@link Editor}\n * instance and an array of matches. If `text` was provided,\n * the matches array will equal [`text`], and if a `match`\n * regex was provided the matches array will be the result of\n * `match.exec` on the matching text. The callback is called\n * after the matching text has been inserted.\n * @public\n */\n }, {\n key: 'onTextInput',\n value: function onTextInput(inputHandler) {\n this._eventManager.registerInputHandler(inputHandler);\n }\n\n /**\n * Unregister all text input handlers\n *\n * @public\n */\n }, {\n key: 'unregisterAllTextInputHandlers',\n value: function unregisterAllTextInputHandlers() {\n this._eventManager.unregisterAllTextInputHandlers();\n }\n\n /**\n * Unregister text input handler by name\n * @param {String} name The name of handler to be removed\n *\n * @public\n */\n }, {\n key: 'unregisterTextInputHandler',\n value: function unregisterTextInputHandler(name) {\n this._eventManager.unregisterInputHandler(name);\n }\n\n /**\n * @param {Function} callback Called when the editor's state (active markups or\n * active sections) has changed, either via user input or programmatically\n */\n }, {\n key: 'inputModeDidChange',\n value: function inputModeDidChange(callback) {\n this.addCallback(CALLBACK_QUEUES.INPUT_MODE_DID_CHANGE, callback);\n }\n\n /**\n * @param {Function} callback This callback will be called before the editor\n * is rendered.\n * @public\n */\n }, {\n key: 'willRender',\n value: function willRender(callback) {\n this.addCallback(CALLBACK_QUEUES.WILL_RENDER, callback);\n }\n\n /**\n * @param {Function} callback This callback will be called after the editor\n * is rendered.\n * @public\n */\n }, {\n key: 'didRender',\n value: function didRender(callback) {\n this.addCallback(CALLBACK_QUEUES.DID_RENDER, callback);\n }\n\n /**\n * @param {Function} callback This callback will be called before deleting.\n * @public\n */\n }, {\n key: 'willDelete',\n value: function willDelete(callback) {\n this.addCallback(CALLBACK_QUEUES.WILL_DELETE, callback);\n }\n\n /**\n * @param {Function} callback This callback will be called after deleting.\n * @public\n */\n }, {\n key: 'didDelete',\n value: function didDelete(callback) {\n this.addCallback(CALLBACK_QUEUES.DID_DELETE, callback);\n }\n\n /**\n * @param {Function} callback This callback will be called before handling new line.\n * @public\n */\n }, {\n key: 'willHandleNewline',\n value: function willHandleNewline(callback) {\n this.addCallback(CALLBACK_QUEUES.WILL_HANDLE_NEWLINE, callback);\n }\n\n /**\n * @param {Function} callback This callback will be called every time the cursor\n * position (or selection) changes.\n * @public\n */\n }, {\n key: 'cursorDidChange',\n value: function cursorDidChange(callback) {\n this.addCallback(CALLBACK_QUEUES.CURSOR_DID_CHANGE, callback);\n }\n }, {\n key: '_rangeDidChange',\n value: function _rangeDidChange() {\n if (this.hasRendered) {\n this.runCallbacks(CALLBACK_QUEUES.CURSOR_DID_CHANGE);\n }\n }\n }, {\n key: '_inputModeDidChange',\n value: function _inputModeDidChange() {\n this.runCallbacks(CALLBACK_QUEUES.INPUT_MODE_DID_CHANGE);\n }\n }, {\n key: '_insertEmptyMarkupSectionAtCursor',\n value: function _insertEmptyMarkupSectionAtCursor() {\n var _this5 = this;\n\n this.run(function (postEditor) {\n var section = postEditor.builder.createMarkupSection('p');\n postEditor.insertSectionBefore(_this5.post.sections, section);\n postEditor.setRange(section.toRange());\n });\n }\n\n /**\n * Toggles the given markup at the editor's current {@link Range}.\n * If the range is collapsed this changes the editor's state so that the\n * next characters typed will be affected. If there is text selected\n * (aka a non-collapsed range), the selections' markup will be toggled.\n * If the editor is not focused and has no active range, nothing happens.\n * @param {String} markup E.g. \"b\", \"em\", \"a\"\n * @public\n * @see PostEditor#toggleMarkup\n */\n }, {\n key: 'toggleMarkup',\n value: function toggleMarkup(markup) {\n markup = this.builder.createMarkup(markup);\n var range = this.range;\n\n if (range.isCollapsed) {\n this._editState.toggleMarkupState(markup);\n this._inputModeDidChange();\n\n // when clicking a button to toggle markup, the button can end up being focused,\n // so ensure the editor is focused\n this._ensureFocus();\n } else {\n this.run(function (postEditor) {\n return postEditor.toggleMarkup(markup, range);\n });\n }\n }\n\n // If the editor has a selection but is not focused, focus it\n }, {\n key: '_ensureFocus',\n value: function _ensureFocus() {\n if (this._hasSelection() && !this._hasFocus()) {\n this.focus();\n }\n }\n }, {\n key: 'focus',\n value: function focus() {\n this.element.focus();\n }\n\n /**\n * Whether there is a selection inside the editor's element.\n * It's possible to have a selection but not have focus.\n * @see #_hasFocus\n * @return {Boolean}\n */\n }, {\n key: '_hasSelection',\n value: function _hasSelection() {\n var cursor = this.cursor;\n\n return this.hasRendered && (cursor._hasCollapsedSelection() || cursor._hasSelection());\n }\n\n /**\n * Whether the editor's element is focused\n * It's possible to be focused but have no selection\n * @see #_hasSelection\n * @return {Boolean}\n */\n }, {\n key: '_hasFocus',\n value: function _hasFocus() {\n return document.activeElement === this.element;\n }\n\n /**\n * Toggles the tagName for the current active section(s). This will skip\n * non-markerable sections. E.g. if the editor's range includes a \"P\" MarkupSection\n * and a CardSection, only the MarkupSection will be toggled.\n * @param {String} tagName The new tagname to change to.\n * @public\n * @see PostEditor#toggleSection\n */\n }, {\n key: 'toggleSection',\n value: function toggleSection(tagName) {\n var _this6 = this;\n\n this.run(function (postEditor) {\n return postEditor.toggleSection(tagName, _this6.range);\n });\n }\n\n /**\n * Finds and runs the first matching key command for the event\n *\n * If multiple commands are bound to a key combination, the\n * first matching one is run.\n *\n * If a command returns `false` then the next matching command\n * is run instead.\n *\n * @param {Event} event The keyboard event triggered by the user\n * @return {Boolean} true when a command was successfully run\n * @private\n */\n }, {\n key: 'handleKeyCommand',\n value: function handleKeyCommand(event) {\n var keyCommands = (0, _mobiledocKitEditorKeyCommands.findKeyCommands)(this.keyCommands, event);\n for (var i = 0; i < keyCommands.length; i++) {\n var keyCommand = keyCommands[i];\n if (keyCommand.run(this) !== false) {\n event.preventDefault();\n return true;\n }\n }\n return false;\n }\n\n /**\n * Inserts the text at the current cursor position. If the editor has\n * no current cursor position, nothing will be inserted. If the editor's\n * range is not collapsed, it will be deleted before insertion.\n *\n * @param {String} text\n * @public\n */\n }, {\n key: 'insertText',\n value: function insertText(text) {\n if (!this.hasCursor()) {\n return;\n }\n if (this.post.isBlank) {\n this._insertEmptyMarkupSectionAtCursor();\n }\n var activeMarkups = this.activeMarkups;\n var range = this.range;\n var position = this.range.head;\n\n this.run(function (postEditor) {\n if (!range.isCollapsed) {\n position = postEditor.deleteRange(range);\n }\n\n postEditor.insertTextWithMarkup(position, text, activeMarkups);\n });\n }\n\n /**\n * Inserts an atom at the current cursor position. If the editor has\n * no current cursor position, nothing will be inserted. If the editor's\n * range is not collapsed, it will be deleted before insertion.\n * @param {String} atomName\n * @param {String} [atomText='']\n * @param {Object} [atomPayload={}]\n * @return {Atom} The inserted atom.\n * @public\n */\n }, {\n key: 'insertAtom',\n value: function insertAtom(atomName) {\n var atomText = arguments.length <= 1 || arguments[1] === undefined ? '' : arguments[1];\n var atomPayload = arguments.length <= 2 || arguments[2] === undefined ? {} : arguments[2];\n\n if (!this.hasCursor()) {\n return;\n }\n if (this.post.isBlank) {\n this._insertEmptyMarkupSectionAtCursor();\n }\n\n var atom = undefined;\n var range = this.range;\n\n this.run(function (postEditor) {\n var position = range.head;\n\n atom = postEditor.builder.createAtom(atomName, atomText, atomPayload);\n if (!range.isCollapsed) {\n position = postEditor.deleteRange(range);\n }\n\n postEditor.insertMarkers(position, [atom]);\n });\n return atom;\n }\n\n /**\n * Inserts a card at the section after the current cursor position. If the editor has\n * no current cursor position, nothing will be inserted. If the editor's\n * range is not collapsed, it will be deleted before insertion. If the cursor is in\n * a blank section, it will be replaced with a card section.\n * The editor's cursor will be placed at the end of the inserted card.\n * @param {String} cardName\n * @param {Object} [cardPayload={}]\n * @param {Boolean} [inEditMode=false] Whether the card should be inserted in edit mode.\n * @return {Card} The inserted Card section.\n * @public\n */\n }, {\n key: 'insertCard',\n value: function insertCard(cardName) {\n var _this7 = this;\n\n var cardPayload = arguments.length <= 1 || arguments[1] === undefined ? {} : arguments[1];\n var inEditMode = arguments.length <= 2 || arguments[2] === undefined ? false : arguments[2];\n\n if (!this.hasCursor()) {\n return;\n }\n if (this.post.isBlank) {\n this._insertEmptyMarkupSectionAtCursor();\n }\n\n var card = undefined;\n var range = this.range;\n\n this.run(function (postEditor) {\n var position = range.tail;\n card = postEditor.builder.createCardSection(cardName, cardPayload);\n if (inEditMode) {\n _this7.editCard(card);\n }\n\n if (!range.isCollapsed) {\n position = postEditor.deleteRange(range);\n }\n\n var section = position.section;\n if (section.isNested) {\n section = section.parent;\n }\n\n if (section.isBlank) {\n postEditor.replaceSection(section, card);\n } else {\n var collection = _this7.post.sections;\n postEditor.insertSectionBefore(collection, card, section.next);\n }\n\n // It is important to explicitly set the range to the end of the card.\n // Otherwise it is possible to create an inconsistent state in the\n // browser. For instance, if the user clicked a button that\n // called `editor.insertCard`, the editor surface may retain\n // the selection but lose focus, and the next keystroke by the user\n // will cause an unexpected DOM mutation (which can wipe out the\n // card).\n // See: https://github.com/bustle/mobiledoc-kit/issues/286\n postEditor.setRange(card.tailPosition());\n });\n return card;\n }\n\n /**\n * @param {integer} x x-position in viewport\n * @param {integer} y y-position in viewport\n * @return {Position|null}\n */\n }, {\n key: 'positionAtPoint',\n value: function positionAtPoint(x, y) {\n return _mobiledocKitUtilsCursorPosition['default'].atPoint(x, y, this);\n }\n\n /**\n * @private\n */\n }, {\n key: '_setCardMode',\n value: function _setCardMode(cardSection, mode) {\n var renderNode = cardSection.renderNode;\n if (renderNode && renderNode.isRendered) {\n var cardNode = renderNode.cardNode;\n cardNode[mode]();\n } else {\n cardSection.setInitialMode(mode);\n }\n }\n }, {\n key: 'triggerEvent',\n value: function triggerEvent(context, eventName, event) {\n this._eventManager._trigger(context, eventName, event);\n }\n }, {\n key: 'addCallback',\n value: function addCallback() {\n var _callbacks;\n\n (_callbacks = this._callbacks).addCallback.apply(_callbacks, arguments);\n }\n }, {\n key: 'addCallbackOnce',\n value: function addCallbackOnce() {\n var _callbacks2;\n\n (_callbacks2 = this._callbacks).addCallbackOnce.apply(_callbacks2, arguments);\n }\n }, {\n key: 'runCallbacks',\n value: function runCallbacks() {\n var _callbacks3;\n\n if (this.isDestroyed) {\n // TODO warn that callback attempted after editor was destroyed\n return;\n }\n (_callbacks3 = this._callbacks).runCallbacks.apply(_callbacks3, arguments);\n }\n }, {\n key: 'builder',\n get: function get() {\n if (!this._builder) {\n this._builder = new _mobiledocKitModelsPostNodeBuilder['default']();\n }\n return this._builder;\n }\n }, {\n key: 'keyCommands',\n get: function get() {\n if (!this._keyCommands) {\n this._keyCommands = [];\n }\n return this._keyCommands;\n }\n }, {\n key: 'cursor',\n get: function get() {\n return new _mobiledocKitUtilsCursor['default'](this);\n }\n\n /**\n * Return the current range for the editor (may be cached).\n * @return {Range}\n */\n }, {\n key: 'range',\n get: function get() {\n return this._editState.range;\n },\n set: function set(newRange) {\n this._editState.updateRange(newRange);\n\n if (this._editState.rangeDidChange()) {\n this._rangeDidChange();\n }\n\n if (this._editState.inputModeDidChange()) {\n this._inputModeDidChange();\n }\n }\n }, {\n key: 'activeSections',\n get: function get() {\n return this._editState.activeSections;\n }\n }, {\n key: 'activeSection',\n get: function get() {\n var activeSections = this.activeSections;\n\n return activeSections[activeSections.length - 1];\n }\n }, {\n key: 'activeMarkups',\n get: function get() {\n return this._editState.activeMarkups;\n }\n }]);\n\n return Editor;\n })();\n\n exports['default'] = Editor;\n});","define('mobiledoc-kit/editor/event-manager', ['exports', 'mobiledoc-kit/utils/assert', 'mobiledoc-kit/utils/parse-utils', 'mobiledoc-kit/utils/array-utils', 'mobiledoc-kit/utils/key', 'mobiledoc-kit/editor/text-input-handler', 'mobiledoc-kit/editor/selection-manager', 'mobiledoc-kit/utils/browser'], function (exports, _mobiledocKitUtilsAssert, _mobiledocKitUtilsParseUtils, _mobiledocKitUtilsArrayUtils, _mobiledocKitUtilsKey, _mobiledocKitEditorTextInputHandler, _mobiledocKitEditorSelectionManager, _mobiledocKitUtilsBrowser) {\n 'use strict';\n\n var _slicedToArray = (function () { function sliceIterator(arr, i) { var _arr = []; var _n = true; var _d = false; var _e = undefined; try { for (var _i = arr[Symbol.iterator](), _s; !(_n = (_s = _i.next()).done); _n = true) { _arr.push(_s.value); if (i && _arr.length === i) break; } } catch (err) { _d = true; _e = err; } finally { try { if (!_n && _i['return']) _i['return'](); } finally { if (_d) throw _e; } } return _arr; } return function (arr, i) { if (Array.isArray(arr)) { return arr; } else if (Symbol.iterator in Object(arr)) { return sliceIterator(arr, i); } else { throw new TypeError('Invalid attempt to destructure non-iterable instance'); } }; })();\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n var ELEMENT_EVENT_TYPES = ['keydown', 'keyup', 'cut', 'copy', 'paste', 'keypress', 'drop'];\n\n var EventManager = (function () {\n function EventManager(editor) {\n _classCallCheck(this, EventManager);\n\n this.editor = editor;\n this.logger = editor.loggerFor('event-manager');\n this._textInputHandler = new _mobiledocKitEditorTextInputHandler['default'](editor);\n this._listeners = [];\n this.modifierKeys = {\n shift: false,\n alt: false,\n ctrl: false\n };\n\n this._selectionManager = new _mobiledocKitEditorSelectionManager['default'](this.editor, this.selectionDidChange.bind(this));\n }\n\n _createClass(EventManager, [{\n key: 'init',\n value: function init() {\n var _this = this;\n\n var element = this.editor.element;\n\n (0, _mobiledocKitUtilsAssert['default'])('Cannot init EventManager without element', !!element);\n\n ELEMENT_EVENT_TYPES.forEach(function (type) {\n _this._addListener(element, type);\n });\n\n this._selectionManager.start();\n }\n }, {\n key: 'registerInputHandler',\n value: function registerInputHandler(inputHandler) {\n this._textInputHandler.register(inputHandler);\n }\n }, {\n key: 'unregisterInputHandler',\n value: function unregisterInputHandler(name) {\n this._textInputHandler.unregister(name);\n }\n }, {\n key: 'unregisterAllTextInputHandlers',\n value: function unregisterAllTextInputHandlers() {\n this._textInputHandler.destroy();\n this._textInputHandler = new _mobiledocKitEditorTextInputHandler['default'](this.editor);\n }\n }, {\n key: '_addListener',\n value: function _addListener(context, type) {\n var _this2 = this;\n\n (0, _mobiledocKitUtilsAssert['default'])('Missing listener for ' + type, !!this[type]);\n\n var listener = function listener(event) {\n return _this2._handleEvent(type, event);\n };\n context.addEventListener(type, listener);\n this._listeners.push([context, type, listener]);\n }\n }, {\n key: '_removeListeners',\n value: function _removeListeners() {\n this._listeners.forEach(function (_ref) {\n var _ref2 = _slicedToArray(_ref, 3);\n\n var context = _ref2[0];\n var type = _ref2[1];\n var listener = _ref2[2];\n\n context.removeEventListener(type, listener);\n });\n this._listeners = [];\n }\n\n // This is primarily useful for programmatically simulating events on the\n // editor from the tests.\n }, {\n key: '_trigger',\n value: function _trigger(context, type, event) {\n (0, _mobiledocKitUtilsArrayUtils.forEach)((0, _mobiledocKitUtilsArrayUtils.filter)(this._listeners, function (_ref3) {\n var _ref32 = _slicedToArray(_ref3, 2);\n\n var _context = _ref32[0];\n var _type = _ref32[1];\n\n return _context === context && _type === type;\n }), function (_ref4) {\n var _ref42 = _slicedToArray(_ref4, 3);\n\n var context = _ref42[0];\n var type = _ref42[1];\n var listener = _ref42[2];\n\n listener.call(context, event);\n });\n }\n }, {\n key: 'destroy',\n value: function destroy() {\n this._textInputHandler.destroy();\n this._selectionManager.destroy();\n this._removeListeners();\n }\n }, {\n key: '_handleEvent',\n value: function _handleEvent(type, event) {\n var element = event.target;\n\n if (!this.isElementAddressable(element)) {\n // abort handling this event\n return true;\n }\n\n this[type](event);\n }\n }, {\n key: 'isElementAddressable',\n value: function isElementAddressable(element) {\n return this.editor.cursor.isAddressable(element);\n }\n }, {\n key: 'selectionDidChange',\n value: function selectionDidChange(selection /*, prevSelection */) {\n var shouldNotify = true;\n var anchorNode = selection.anchorNode;\n\n if (!this.isElementAddressable(anchorNode)) {\n if (!this.editor.range.isBlank) {\n // Selection changed from something addressable to something\n // not-addressable -- e.g., blur event, user clicked outside editor,\n // etc\n shouldNotify = true;\n } else {\n // selection changes wholly outside the editor should not trigger\n // change notifications\n shouldNotify = false;\n }\n }\n\n if (shouldNotify) {\n this.editor._readRangeFromDOM();\n }\n }\n }, {\n key: 'keypress',\n value: function keypress(event) {\n var editor = this.editor;\n var _textInputHandler = this._textInputHandler;\n\n if (!editor.hasCursor()) {\n return;\n }\n\n var key = _mobiledocKitUtilsKey['default'].fromEvent(event);\n if (!key.isPrintable()) {\n return;\n } else {\n event.preventDefault();\n }\n\n _textInputHandler.handle(key.toString());\n }\n }, {\n key: 'keydown',\n value: function keydown(event) {\n var editor = this.editor;\n\n if (!editor.hasCursor()) {\n return;\n }\n if (!editor.isEditable) {\n return;\n }\n\n var key = _mobiledocKitUtilsKey['default'].fromEvent(event);\n this._updateModifiersFromKey(key, { isDown: true });\n\n if (editor.handleKeyCommand(event)) {\n return;\n }\n\n if (editor.post.isBlank) {\n editor._insertEmptyMarkupSectionAtCursor();\n }\n\n var range = editor.range;\n\n switch (true) {\n // FIXME This should be restricted to only card/atom boundaries\n case key.isHorizontalArrowWithoutModifiersOtherThanShift():\n var newRange = undefined;\n if (key.isShift()) {\n newRange = range.extend(key.direction * 1);\n } else {\n newRange = range.move(key.direction);\n }\n\n editor.selectRange(newRange);\n event.preventDefault();\n break;\n case key.isDelete():\n var direction = key.direction;\n\n var unit = 'char';\n if (this.modifierKeys.alt && _mobiledocKitUtilsBrowser['default'].isMac()) {\n unit = 'word';\n } else if (this.modifierKeys.ctrl && _mobiledocKitUtilsBrowser['default'].isWin()) {\n unit = 'word';\n }\n editor.performDelete({ direction: direction, unit: unit });\n event.preventDefault();\n break;\n case key.isEnter():\n editor.handleNewline(event);\n break;\n case key.isTab():\n // Handle tab here because it does not fire a `keypress` event\n event.preventDefault();\n this._textInputHandler.handle(key.toString());\n break;\n }\n }\n }, {\n key: 'keyup',\n value: function keyup(event) {\n var editor = this.editor;\n\n if (!editor.hasCursor()) {\n return;\n }\n var key = _mobiledocKitUtilsKey['default'].fromEvent(event);\n this._updateModifiersFromKey(key, { isDown: false });\n }\n }, {\n key: 'cut',\n value: function cut(event) {\n event.preventDefault();\n\n this.copy(event);\n this.editor.performDelete();\n }\n }, {\n key: 'copy',\n value: function copy(event) {\n event.preventDefault();\n\n var editor = this.editor;\n var _editor = this.editor;\n var range = _editor.range;\n var post = _editor.post;\n\n post = post.trimTo(range);\n\n var data = {\n html: editor.serializePost(post, 'html'),\n text: editor.serializePost(post, 'text'),\n mobiledoc: editor.serializePost(post, 'mobiledoc')\n };\n\n (0, _mobiledocKitUtilsParseUtils.setClipboardData)(event, data, window);\n }\n }, {\n key: 'paste',\n value: function paste(event) {\n event.preventDefault();\n\n var editor = this.editor;\n\n var range = editor.range;\n\n if (!range.isCollapsed) {\n editor.performDelete();\n }\n\n if (editor.post.isBlank) {\n editor._insertEmptyMarkupSectionAtCursor();\n }\n\n var position = editor.range.head;\n var targetFormat = this.modifierKeys.shift ? 'text' : 'html';\n var pastedPost = (0, _mobiledocKitUtilsParseUtils.parsePostFromPaste)(event, editor, { targetFormat: targetFormat });\n\n editor.run(function (postEditor) {\n var nextPosition = postEditor.insertPost(position, pastedPost);\n postEditor.setRange(nextPosition);\n });\n }\n }, {\n key: 'drop',\n value: function drop(event) {\n event.preventDefault();\n\n var x = event.clientX;\n var y = event.clientY;\n var editor = this.editor;\n\n var position = editor.positionAtPoint(x, y);\n if (!position) {\n this.logger.log('Could not find drop position');\n return;\n }\n\n var post = (0, _mobiledocKitUtilsParseUtils.parsePostFromDrop)(event, editor, { logger: this.logger });\n if (!post) {\n this.logger.log('Could not determine post from drop event');\n return;\n }\n\n editor.run(function (postEditor) {\n var nextPosition = postEditor.insertPost(position, post);\n postEditor.setRange(nextPosition);\n });\n }\n }, {\n key: '_updateModifiersFromKey',\n value: function _updateModifiersFromKey(key, _ref5) {\n var isDown = _ref5.isDown;\n\n if (key.isShiftKey()) {\n this.modifierKeys.shift = isDown;\n } else if (key.isAltKey()) {\n this.modifierKeys.alt = isDown;\n } else if (key.isCtrlKey()) {\n this.modifierKeys.ctrl = isDown;\n }\n }\n }]);\n\n return EventManager;\n })();\n\n exports['default'] = EventManager;\n});","define('mobiledoc-kit/editor/key-commands', ['exports', 'mobiledoc-kit/utils/key', 'mobiledoc-kit/utils/array-utils', 'mobiledoc-kit/utils/assert', 'mobiledoc-kit/utils/browser', 'mobiledoc-kit/editor/ui'], function (exports, _mobiledocKitUtilsKey, _mobiledocKitUtilsArrayUtils, _mobiledocKitUtilsAssert, _mobiledocKitUtilsBrowser, _mobiledocKitEditorUi) {\n 'use strict';\n\n exports.buildKeyCommand = buildKeyCommand;\n exports.validateKeyCommand = validateKeyCommand;\n exports.findKeyCommands = findKeyCommands;\n\n function _toArray(arr) { return Array.isArray(arr) ? arr : Array.from(arr); }\n\n function selectAll(editor) {\n var post = editor.post;\n\n editor.selectRange(post.toRange());\n }\n\n function gotoStartOfLine(editor) {\n var range = editor.range;\n var section = range.tail.section;\n\n editor.run(function (postEditor) {\n postEditor.setRange(section.headPosition());\n });\n }\n\n function gotoEndOfLine(editor) {\n var range = editor.range;\n var section = range.tail.section;\n\n editor.run(function (postEditor) {\n postEditor.setRange(section.tailPosition());\n });\n }\n\n function deleteToEndOfSection(editor) {\n var range = editor.range;\n\n if (range.isCollapsed) {\n var _range = range;\n var head = _range.head;\n var section = _range.head.section;\n\n range = head.toRange(section.tailPosition());\n }\n editor.run(function (postEditor) {\n var nextPosition = postEditor.deleteRange(range);\n postEditor.setRange(nextPosition);\n });\n }\n\n var DEFAULT_KEY_COMMANDS = [{\n str: 'META+B',\n run: function run(editor) {\n editor.toggleMarkup('strong');\n }\n }, {\n str: 'CTRL+B',\n run: function run(editor) {\n editor.toggleMarkup('strong');\n }\n }, {\n str: 'META+I',\n run: function run(editor) {\n editor.toggleMarkup('em');\n }\n }, {\n str: 'CTRL+I',\n run: function run(editor) {\n editor.toggleMarkup('em');\n }\n }, {\n str: 'CTRL+K',\n run: function run(editor) {\n if (_mobiledocKitUtilsBrowser['default'].isMac()) {\n return deleteToEndOfSection(editor);\n } else if (_mobiledocKitUtilsBrowser['default'].isWin()) {\n return (0, _mobiledocKitEditorUi.toggleLink)(editor);\n }\n }\n }, {\n str: 'CTRL+A',\n run: function run(editor) {\n if (_mobiledocKitUtilsBrowser['default'].isMac()) {\n gotoStartOfLine(editor);\n } else {\n selectAll(editor);\n }\n }\n }, {\n str: 'META+A',\n run: function run(editor) {\n if (_mobiledocKitUtilsBrowser['default'].isMac()) {\n selectAll(editor);\n }\n }\n }, {\n str: 'CTRL+E',\n run: function run(editor) {\n if (_mobiledocKitUtilsBrowser['default'].isMac()) {\n gotoEndOfLine(editor);\n }\n }\n }, {\n str: 'META+K',\n run: function run(editor) {\n return (0, _mobiledocKitEditorUi.toggleLink)(editor);\n }\n\n }, {\n str: 'META+Z',\n run: function run(editor) {\n editor.run(function (postEditor) {\n postEditor.undoLastChange();\n });\n }\n }, {\n str: 'META+SHIFT+Z',\n run: function run(editor) {\n editor.run(function (postEditor) {\n postEditor.redoLastChange();\n });\n }\n }, {\n str: 'CTRL+Z',\n run: function run(editor) {\n if (_mobiledocKitUtilsBrowser['default'].isMac()) {\n return false;\n }\n editor.run(function (postEditor) {\n return postEditor.undoLastChange();\n });\n }\n }, {\n str: 'CTRL+SHIFT+Z',\n run: function run(editor) {\n if (_mobiledocKitUtilsBrowser['default'].isMac()) {\n return false;\n }\n editor.run(function (postEditor) {\n return postEditor.redoLastChange();\n });\n }\n }];\n\n exports.DEFAULT_KEY_COMMANDS = DEFAULT_KEY_COMMANDS;\n function modifierNamesToMask(modiferNames) {\n var defaultVal = 0;\n return (0, _mobiledocKitUtilsArrayUtils.reduce)(modiferNames, function (sum, name) {\n var modifier = _mobiledocKitUtilsKey.MODIFIERS[name.toUpperCase()];\n (0, _mobiledocKitUtilsAssert['default'])('No modifier named \"' + name + '\" found', !!modifier);\n return sum + modifier;\n }, defaultVal);\n }\n\n function characterToCode(character) {\n var upperCharacter = character.toUpperCase();\n var special = _mobiledocKitUtilsKey.SPECIAL_KEYS[upperCharacter];\n if (special) {\n return special;\n } else {\n (0, _mobiledocKitUtilsAssert['default'])('Only 1 character can be used in a key command str (got \"' + character + '\")', character.length === 1);\n return upperCharacter.charCodeAt(0);\n }\n }\n\n function buildKeyCommand(keyCommand) {\n var str = keyCommand.str;\n\n if (!str) {\n return keyCommand;\n }\n (0, _mobiledocKitUtilsAssert['default'])('[deprecation] Key commands no longer use the `modifier` property', !keyCommand.modifier);\n\n var _str$split$reverse = str.split('+').reverse();\n\n var _str$split$reverse2 = _toArray(_str$split$reverse);\n\n var character = _str$split$reverse2[0];\n\n var modifierNames = _str$split$reverse2.slice(1);\n\n keyCommand.modifierMask = modifierNamesToMask(modifierNames);\n keyCommand.code = characterToCode(character);\n\n return keyCommand;\n }\n\n function validateKeyCommand(keyCommand) {\n return !!keyCommand.code && !!keyCommand.run;\n }\n\n function findKeyCommands(keyCommands, keyEvent) {\n var key = _mobiledocKitUtilsKey['default'].fromEvent(keyEvent);\n\n return (0, _mobiledocKitUtilsArrayUtils.filter)(keyCommands, function (_ref) {\n var modifierMask = _ref.modifierMask;\n var code = _ref.code;\n\n return key.keyCode === code && key.modifierMask === modifierMask;\n });\n }\n});","define('mobiledoc-kit/editor/mutation-handler', ['exports', 'mobiledoc-kit/utils/set', 'mobiledoc-kit/utils/array-utils', 'mobiledoc-kit/utils/assert', 'mobiledoc-kit/utils/dom-utils'], function (exports, _mobiledocKitUtilsSet, _mobiledocKitUtilsArrayUtils, _mobiledocKitUtilsAssert, _mobiledocKitUtilsDomUtils) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n var MUTATION = {\n NODES_CHANGED: 'childList',\n CHARACTER_DATA: 'characterData'\n };\n\n var MutationHandler = (function () {\n function MutationHandler(editor) {\n var _this = this;\n\n _classCallCheck(this, MutationHandler);\n\n this.editor = editor;\n this.logger = editor.loggerFor('mutation-handler');\n this.renderTree = null;\n this._isObserving = false;\n\n this._observer = new MutationObserver(function (mutations) {\n _this._handleMutations(mutations);\n });\n }\n\n _createClass(MutationHandler, [{\n key: 'init',\n value: function init() {\n this.startObserving();\n }\n }, {\n key: 'destroy',\n value: function destroy() {\n this.stopObserving();\n this._observer = null;\n }\n }, {\n key: 'suspendObservation',\n value: function suspendObservation(callback) {\n this.stopObserving();\n callback();\n this.startObserving();\n }\n }, {\n key: 'stopObserving',\n value: function stopObserving() {\n if (this._isObserving) {\n this._isObserving = false;\n this._observer.disconnect();\n }\n }\n }, {\n key: 'startObserving',\n value: function startObserving() {\n if (!this._isObserving) {\n var editor = this.editor;\n\n (0, _mobiledocKitUtilsAssert['default'])('Cannot observe un-rendered editor', editor.hasRendered);\n\n this._isObserving = true;\n this.renderTree = editor._renderTree;\n\n this._observer.observe(editor.element, {\n characterData: true,\n childList: true,\n subtree: true\n });\n }\n }\n }, {\n key: 'reparsePost',\n value: function reparsePost() {\n this.editor._reparsePost();\n }\n }, {\n key: 'reparseSections',\n value: function reparseSections(sections) {\n this.editor._reparseSections(sections);\n }\n\n /**\n * for each mutation:\n * * find the target nodes:\n * * if nodes changed, target nodes are:\n * * added nodes\n * * the target from which removed nodes were removed\n * * if character data changed\n * * target node is the mutation event's target (text node)\n * * filter out nodes that are no longer attached (parentNode is null)\n * * for each remaining node:\n * * find its section, add to sections-to-reparse\n * * if no section, reparse all (and break)\n */\n }, {\n key: '_handleMutations',\n value: function _handleMutations(mutations) {\n var reparsePost = false;\n var sections = new _mobiledocKitUtilsSet['default']();\n\n for (var i = 0; i < mutations.length; i++) {\n if (reparsePost) {\n break;\n }\n\n var nodes = this._findTargetNodes(mutations[i]);\n\n for (var j = 0; j < nodes.length; j++) {\n var node = nodes[j];\n var renderNode = this._findRenderNodeFromNode(node);\n if (renderNode) {\n if (renderNode.reparsesMutationOfChildNode(node)) {\n var section = this._findSectionFromRenderNode(renderNode);\n if (section) {\n sections.add(section);\n } else {\n reparsePost = true;\n }\n }\n } else {\n reparsePost = true;\n break;\n }\n }\n }\n\n if (reparsePost) {\n this.logger.log('reparsePost (' + mutations.length + ' mutations)');\n this.reparsePost();\n } else if (sections.length) {\n this.logger.log('reparse ' + sections.length + ' sections (' + mutations.length + ' mutations)');\n this.reparseSections(sections.toArray());\n }\n }\n }, {\n key: '_findTargetNodes',\n value: function _findTargetNodes(mutation) {\n var nodes = [];\n\n switch (mutation.type) {\n case MUTATION.CHARACTER_DATA:\n nodes.push(mutation.target);\n break;\n case MUTATION.NODES_CHANGED:\n (0, _mobiledocKitUtilsArrayUtils.forEach)(mutation.addedNodes, function (n) {\n return nodes.push(n);\n });\n if (mutation.removedNodes.length) {\n nodes.push(mutation.target);\n }\n break;\n }\n\n var element = this.editor.element;\n var attachedNodes = (0, _mobiledocKitUtilsArrayUtils.filter)(nodes, function (node) {\n return (0, _mobiledocKitUtilsDomUtils.containsNode)(element, node);\n });\n return attachedNodes;\n }\n }, {\n key: '_findSectionRenderNodeFromNode',\n value: function _findSectionRenderNodeFromNode(node) {\n return this.renderTree.findRenderNodeFromElement(node, function (rn) {\n return rn.postNode.isSection;\n });\n }\n }, {\n key: '_findRenderNodeFromNode',\n value: function _findRenderNodeFromNode(node) {\n return this.renderTree.findRenderNodeFromElement(node);\n }\n }, {\n key: '_findSectionFromRenderNode',\n value: function _findSectionFromRenderNode(renderNode) {\n var sectionRenderNode = this._findSectionRenderNodeFromNode(renderNode.element);\n return sectionRenderNode && sectionRenderNode.postNode;\n }\n }]);\n\n return MutationHandler;\n })();\n\n exports['default'] = MutationHandler;\n});","define('mobiledoc-kit/editor/post', ['exports', 'mobiledoc-kit/utils/cursor/position', 'mobiledoc-kit/utils/cursor/range', 'mobiledoc-kit/utils/array-utils', 'mobiledoc-kit/utils/key', 'mobiledoc-kit/models/lifecycle-callbacks', 'mobiledoc-kit/utils/assert', 'mobiledoc-kit/utils/dom-utils', 'mobiledoc-kit/editor/post/post-inserter', 'mobiledoc-kit/utils/deprecate', 'mobiledoc-kit/utils/to-range'], function (exports, _mobiledocKitUtilsCursorPosition, _mobiledocKitUtilsCursorRange, _mobiledocKitUtilsArrayUtils, _mobiledocKitUtilsKey, _mobiledocKitModelsLifecycleCallbacks, _mobiledocKitUtilsAssert, _mobiledocKitUtilsDomUtils, _mobiledocKitEditorPostPostInserter, _mobiledocKitUtilsDeprecate, _mobiledocKitUtilsToRange) {\n 'use strict';\n\n var _slicedToArray = (function () { function sliceIterator(arr, i) { var _arr = []; var _n = true; var _d = false; var _e = undefined; try { for (var _i = arr[Symbol.iterator](), _s; !(_n = (_s = _i.next()).done); _n = true) { _arr.push(_s.value); if (i && _arr.length === i) break; } } catch (err) { _d = true; _e = err; } finally { try { if (!_n && _i['return']) _i['return'](); } finally { if (_d) throw _e; } } return _arr; } return function (arr, i) { if (Array.isArray(arr)) { return arr; } else if (Symbol.iterator in Object(arr)) { return sliceIterator(arr, i); } else { throw new TypeError('Invalid attempt to destructure non-iterable instance'); } }; })();\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n var FORWARD = _mobiledocKitUtilsKey.DIRECTION.FORWARD;\n var BACKWARD = _mobiledocKitUtilsKey.DIRECTION.BACKWARD;\n\n function isListSectionTagName(tagName) {\n return tagName === 'ul' || tagName === 'ol';\n }\n\n var CALLBACK_QUEUES = {\n BEFORE_COMPLETE: 'beforeComplete',\n COMPLETE: 'complete',\n AFTER_COMPLETE: 'afterComplete'\n };\n\n /**\n * The PostEditor is used to modify a post. It should not be instantiated directly.\n * Instead, a new instance of a PostEditor is created by the editor and passed\n * as the argument to the callback in {@link Editor#run}.\n *\n * Usage:\n * ```\n * editor.run((postEditor) => {\n * // postEditor is an instance of PostEditor that can operate on the\n * // editor's post\n * });\n * ```\n */\n\n var PostEditor = (function () {\n /**\n * @private\n */\n\n function PostEditor(editor) {\n var _this = this;\n\n _classCallCheck(this, PostEditor);\n\n this.editor = editor;\n this.builder = this.editor.builder;\n this._callbacks = new _mobiledocKitModelsLifecycleCallbacks['default']((0, _mobiledocKitUtilsArrayUtils.values)(CALLBACK_QUEUES));\n\n this._didComplete = false;\n\n this._renderRange = function () {\n return _this.editor.selectRange(_this._range);\n };\n this._postDidChange = function () {\n return _this.editor._postDidChange();\n };\n this._rerender = function () {\n return _this.editor.rerender();\n };\n }\n\n _createClass(PostEditor, [{\n key: 'addCallback',\n value: function addCallback() {\n var _callbacks;\n\n (_callbacks = this._callbacks).addCallback.apply(_callbacks, arguments);\n }\n }, {\n key: 'addCallbackOnce',\n value: function addCallbackOnce() {\n var _callbacks2;\n\n (_callbacks2 = this._callbacks).addCallbackOnce.apply(_callbacks2, arguments);\n }\n }, {\n key: 'runCallbacks',\n value: function runCallbacks() {\n var _callbacks3;\n\n (_callbacks3 = this._callbacks).runCallbacks.apply(_callbacks3, arguments);\n }\n }, {\n key: 'begin',\n value: function begin() {\n // cache the editor's range\n this._range = this.editor.range;\n }\n\n /**\n * Schedules to select the given range on the editor after the postEditor\n * has completed its work. This also updates the postEditor's active range\n * (so that multiple calls to range-changing methods on the postEditor will\n * update the correct range).\n *\n * Usage:\n * let range = editor.range;\n * editor.run(postEditor => {\n * let nextPosition = postEditor.deleteRange(range);\n *\n * // Will position the editor's cursor at `nextPosition` after\n * // the postEditor finishes work and the editor rerenders.\n * postEditor.setRange(nextPosition);\n * });\n * @param {Range|Position} range\n * @public\n */\n }, {\n key: 'setRange',\n value: function setRange(range) {\n range = (0, _mobiledocKitUtilsToRange['default'])(range);\n\n // TODO validate that the range is valid\n // (does not contain marked-for-removal head or tail sections?)\n this._range = range;\n this.scheduleAfterRender(this._renderRange, true);\n }\n\n /**\n * Delete a range from the post\n *\n * Usage:\n * ```\n * let { range } = editor;\n * editor.run((postEditor) => {\n * let nextPosition = postEditor.deleteRange(range);\n * postEditor.setRange(nextPosition);\n * });\n * ```\n * @param {Range} range Cursor Range object with head and tail Positions\n * @return {Position} The position where the cursor would go after deletion\n * @public\n */\n }, {\n key: 'deleteRange',\n value: function deleteRange(range) {\n (0, _mobiledocKitUtilsAssert['default'])(\"Must pass MobiledocKit Range to `deleteRange`\", range instanceof _mobiledocKitUtilsCursorRange['default']);\n\n var head = range.head;\n var headSection = range.head.section;\n var tail = range.tail;\n var tailSection = range.tail.section;\n var post = this.editor.post;\n\n if (headSection === tailSection) {\n return this.cutSection(headSection, head, tail);\n }\n\n var nextSection = headSection.nextLeafSection();\n\n var nextPos = this.cutSection(headSection, head, headSection.tailPosition());\n // cutSection can replace the section, so re-read headSection here\n headSection = nextPos.section;\n\n // Remove sections in the middle of the range\n while (nextSection !== tailSection) {\n var tmp = nextSection;\n nextSection = nextSection.nextLeafSection();\n this.removeSection(tmp);\n }\n\n var tailPos = this.cutSection(tailSection, tailSection.headPosition(), tail);\n // cutSection can replace the section, so re-read tailSection here\n tailSection = tailPos.section;\n\n if (tailSection.isBlank) {\n this.removeSection(tailSection);\n } else {\n // If head and tail sections are markerable, join them\n // Note: They may not be the same section type. E.g. this may join\n // a tail section that was a list item onto a markup section, or vice versa.\n // (This is the desired behavior.)\n if (headSection.isMarkerable && tailSection.isMarkerable) {\n headSection.join(tailSection);\n this._markDirty(headSection);\n this.removeSection(tailSection);\n } else if (headSection.isBlank) {\n this.removeSection(headSection);\n nextPos = tailPos;\n }\n }\n\n if (post.isBlank) {\n post.sections.append(this.builder.createMarkupSection('p'));\n nextPos = post.headPosition();\n }\n\n return nextPos;\n }\n\n /**\n * Note: This method may replace `section` with a different section.\n *\n * \"Cut\" out the part of the section inside `headOffset` and `tailOffset`.\n * If section is markerable this splits markers that straddle the head or tail (if necessary),\n * and removes markers that are wholly inside the offsets.\n * If section is a card, this may replace it with a blank markup section if the\n * positions contain the entire card.\n *\n * @param {Section} section\n * @param {Position} head\n * @param {Position} tail\n * @return {Position}\n * @private\n */\n }, {\n key: 'cutSection',\n value: function cutSection(section, head, tail) {\n var _this2 = this;\n\n (0, _mobiledocKitUtilsAssert['default'])('Must pass head position and tail position to `cutSection`', head instanceof _mobiledocKitUtilsCursorPosition['default'] && tail instanceof _mobiledocKitUtilsCursorPosition['default']);\n (0, _mobiledocKitUtilsAssert['default'])('Must pass positions within same section to `cutSection`', head.section === tail.section);\n\n if (section.isBlank || head.isEqual(tail)) {\n return head;\n }\n if (section.isCardSection) {\n if (head.isHead() && tail.isTail()) {\n var newSection = this.builder.createMarkupSection();\n this.replaceSection(section, newSection);\n return newSection.headPosition();\n } else {\n return tail;\n }\n }\n\n var range = head.toRange(tail);\n this.splitMarkers(range).forEach(function (m) {\n return _this2.removeMarker(m);\n });\n\n return head;\n }\n }, {\n key: '_coalesceMarkers',\n value: function _coalesceMarkers(section) {\n if (section.isMarkerable) {\n this._removeBlankMarkers(section);\n this._joinSimilarMarkers(section);\n }\n }\n }, {\n key: '_removeBlankMarkers',\n value: function _removeBlankMarkers(section) {\n var _this3 = this;\n\n (0, _mobiledocKitUtilsArrayUtils.forEach)((0, _mobiledocKitUtilsArrayUtils.filter)(section.markers, function (m) {\n return m.isBlank;\n }), function (m) {\n return _this3.removeMarker(m);\n });\n }\n\n // joins markers that have identical markups\n }, {\n key: '_joinSimilarMarkers',\n value: function _joinSimilarMarkers(section) {\n var marker = section.markers.head;\n var nextMarker = undefined;\n while (marker && marker.next) {\n nextMarker = marker.next;\n\n if (marker.canJoin(nextMarker)) {\n nextMarker.value = marker.value + nextMarker.value;\n this._markDirty(nextMarker);\n this.removeMarker(marker);\n }\n\n marker = nextMarker;\n }\n }\n }, {\n key: 'removeMarker',\n value: function removeMarker(marker) {\n this._scheduleForRemoval(marker);\n if (marker.section) {\n this._markDirty(marker.section);\n marker.section.markers.remove(marker);\n }\n }\n }, {\n key: '_scheduleForRemoval',\n value: function _scheduleForRemoval(postNode) {\n var _this4 = this;\n\n if (postNode.renderNode) {\n postNode.renderNode.scheduleForRemoval();\n\n this.scheduleRerender();\n this.scheduleDidUpdate();\n }\n var removedAdjacentToList = postNode.prev && postNode.prev.isListSection || postNode.next && postNode.next.isListSection;\n if (removedAdjacentToList) {\n this.addCallback(CALLBACK_QUEUES.BEFORE_COMPLETE, function () {\n return _this4._joinContiguousListSections();\n });\n }\n }\n }, {\n key: '_joinContiguousListSections',\n value: function _joinContiguousListSections() {\n var _this5 = this;\n\n var post = this.editor.post;\n\n var range = this._range;\n var prev = undefined;\n var groups = [];\n var currentGroup = undefined;\n\n // FIXME do we need to force a re-render of the range if changed sections\n // are contained within the range?\n var updatedHead = null;\n (0, _mobiledocKitUtilsArrayUtils.forEach)(post.sections, function (section) {\n if (prev && prev.isListSection && section.isListSection && prev.tagName === section.tagName) {\n\n currentGroup = currentGroup || [prev];\n currentGroup.push(section);\n } else {\n if (currentGroup) {\n groups.push(currentGroup);\n }\n currentGroup = null;\n }\n prev = section;\n });\n\n if (currentGroup) {\n groups.push(currentGroup);\n }\n\n (0, _mobiledocKitUtilsArrayUtils.forEach)(groups, function (group) {\n var list = group[0];\n (0, _mobiledocKitUtilsArrayUtils.forEach)(group, function (listSection) {\n if (listSection === list) {\n return;\n }\n\n var currentHead = range.head;\n var prevPosition = undefined;\n\n // FIXME is there a currentHead if there is no range?\n // is the current head a list item in the section\n if (!range.isBlank && currentHead.section.isListItem && currentHead.section.parent === listSection) {\n prevPosition = list.tailPosition();\n }\n _this5._joinListSections(list, listSection);\n if (prevPosition) {\n updatedHead = prevPosition.move(FORWARD);\n }\n });\n });\n\n if (updatedHead) {\n this.setRange(updatedHead);\n }\n }\n }, {\n key: '_joinListSections',\n value: function _joinListSections(baseList, nextList) {\n baseList.join(nextList);\n this._markDirty(baseList);\n this.removeSection(nextList);\n }\n }, {\n key: '_markDirty',\n value: function _markDirty(postNode) {\n var _this6 = this;\n\n if (postNode.renderNode) {\n postNode.renderNode.markDirty();\n\n this.scheduleRerender();\n this.scheduleDidUpdate();\n }\n if (postNode.section) {\n this._markDirty(postNode.section);\n }\n if (postNode.isMarkerable) {\n this.addCallback(CALLBACK_QUEUES.BEFORE_COMPLETE, function () {\n return _this6._coalesceMarkers(postNode);\n });\n }\n }\n\n /**\n * @param {Position} position object with {section, offset} the marker and offset to delete from\n * @param {Number} direction The direction to delete in (default is BACKWARD)\n * @return {Position} for positioning the cursor\n * @public\n * @deprecated after v0.10.3\n */\n }, {\n key: 'deleteFrom',\n value: function deleteFrom(position) {\n var direction = arguments.length <= 1 || arguments[1] === undefined ? _mobiledocKitUtilsKey.DIRECTION.BACKWARD : arguments[1];\n\n (0, _mobiledocKitUtilsDeprecate['default'])(\"`postEditor#deleteFrom is deprecated. Use `deleteAtPosition(position, direction=BACKWARD, {unit}={unit: 'char'})` instead\");\n return this.deleteAtPosition(position, direction, { unit: 'char' });\n }\n\n /**\n * Delete 1 `unit` (can be 'char' or 'word') in the given `direction` at the given\n * `position`. In almost all cases this will be equivalent to deleting the range formed\n * by expanding the position 1 unit in the given direction. The exception is when deleting\n * backward from the beginning of a list item, which reverts the list item into a markup section\n * instead of joining it with its previous list item (if any).\n *\n * Usage:\n *\n * let position = section.tailPosition();\n * // Section has text of \"Howdy!\"\n * editor.run((postEditor) => {\n * postEditor.deleteAtPosition(position);\n * });\n * // section has text of \"Howdy\"\n *\n * @param {Position} position The position to delete at\n * @param {Direction} [direction=DIRECTION.BACKWARD] direction The direction to delete in\n * @param {Object} [options]\n * @param {String} [options.unit=\"char\"] The unit of deletion (\"word\" or \"char\")\n * @return {Position}\n */\n }, {\n key: 'deleteAtPosition',\n value: function deleteAtPosition(position) {\n var direction = arguments.length <= 1 || arguments[1] === undefined ? _mobiledocKitUtilsKey.DIRECTION.BACKWARD : arguments[1];\n\n var _ref = arguments.length <= 2 || arguments[2] === undefined ? { unit: 'char' } : arguments[2];\n\n var unit = _ref.unit;\n\n if (direction === _mobiledocKitUtilsKey.DIRECTION.BACKWARD) {\n return this._deleteAtPositionBackward(position, unit);\n } else {\n return this._deleteAtPositionForward(position, unit);\n }\n }\n }, {\n key: '_deleteAtPositionBackward',\n value: function _deleteAtPositionBackward(position, unit) {\n if (position.isHead() && position.section.isListItem) {\n this.toggleSection('p', position);\n return this._range.head;\n } else {\n var prevPosition = unit === 'word' ? position.moveWord(BACKWARD) : position.move(BACKWARD);\n var range = prevPosition.toRange(position);\n return this.deleteRange(range);\n }\n }\n }, {\n key: '_deleteAtPositionForward',\n value: function _deleteAtPositionForward(position, unit) {\n var nextPosition = unit === 'word' ? position.moveWord(FORWARD) : position.move(FORWARD);\n var range = position.toRange(nextPosition);\n return this.deleteRange(range);\n }\n\n /**\n * Split markers at two positions, once at the head, and if necessary once\n * at the tail.\n *\n * Usage:\n * ```\n * let range = editor.range;\n * editor.run((postEditor) => {\n * postEditor.splitMarkers(range);\n * });\n * ```\n * The return value will be marker object completely inside the offsets\n * provided. Markers outside of the split may also have been modified.\n *\n * @param {Range} markerRange\n * @return {Array} of markers that are inside the split\n * @private\n */\n }, {\n key: 'splitMarkers',\n value: function splitMarkers(range) {\n var post = this.editor.post;\n var head = range.head;\n var tail = range.tail;\n\n this.splitSectionMarkerAtOffset(head.section, head.offset);\n this.splitSectionMarkerAtOffset(tail.section, tail.offset);\n\n return post.markersContainedByRange(range);\n }\n }, {\n key: 'splitSectionMarkerAtOffset',\n value: function splitSectionMarkerAtOffset(section, offset) {\n var _this7 = this;\n\n var edit = section.splitMarkerAtOffset(offset);\n edit.removed.forEach(function (m) {\n return _this7.removeMarker(m);\n });\n }\n\n /**\n * Split the section at the position.\n *\n * Usage:\n * ```\n * let position = editor.cursor.offsets.head;\n * editor.run((postEditor) => {\n * postEditor.splitSection(position);\n * });\n * // Will result in the creation of two new sections\n * // replacing the old one at the cursor position\n * ```\n * The return value will be the two new sections. One or both of these\n * sections can be blank (contain only a blank marker), for example if the\n * headMarkerOffset is 0.\n *\n * @param {Position} position\n * @return {Array} new sections, one for the first half and one for the second (either one can be null)\n * @public\n */\n }, {\n key: 'splitSection',\n value: function splitSection(position) {\n var _this8 = this;\n\n var section = position.section;\n\n if (section.isCardSection) {\n return this._splitCardSection(section, position);\n } else if (section.isListItem) {\n var isLastAndBlank = section.isBlank && !section.next;\n if (isLastAndBlank) {\n // if is last, replace the item with a blank markup section\n var _parent = section.parent;\n var collection = this.editor.post.sections;\n var blank = this.builder.createMarkupSection();\n this.removeSection(section);\n this.insertSectionBefore(collection, blank, _parent.next);\n\n return [null, blank];\n } else {\n var _splitListItem2 = this._splitListItem(section, position);\n\n var _splitListItem22 = _slicedToArray(_splitListItem2, 2);\n\n var pre = _splitListItem22[0];\n var post = _splitListItem22[1];\n\n return [pre, post];\n }\n } else {\n var splitSections = section.splitAtPosition(position);\n splitSections.forEach(function (s) {\n return _this8._coalesceMarkers(s);\n });\n this._replaceSection(section, splitSections);\n\n return splitSections;\n }\n }\n\n /**\n * @param {Section} cardSection\n * @param {Position} position to split at\n * @return {Section[]} 2-item array of pre and post-split sections\n * @private\n */\n }, {\n key: '_splitCardSection',\n value: function _splitCardSection(cardSection, position) {\n var offset = position.offset;\n\n (0, _mobiledocKitUtilsAssert['default'])('Cards section must be split at offset 0 or 1', offset === 0 || offset === 1);\n\n var newSection = this.builder.createMarkupSection();\n var nextSection = undefined;\n var surroundingSections = undefined;\n\n if (offset === 0) {\n nextSection = cardSection;\n surroundingSections = [newSection, cardSection];\n } else {\n nextSection = cardSection.next;\n surroundingSections = [cardSection, newSection];\n }\n\n var collection = this.editor.post.sections;\n this.insertSectionBefore(collection, newSection, nextSection);\n\n return surroundingSections;\n }\n\n /**\n * @param {Section} section\n * @param {Section} newSection\n * @return null\n * @public\n */\n }, {\n key: 'replaceSection',\n value: function replaceSection(section, newSection) {\n if (!section) {\n // FIXME should a falsy section be a valid argument?\n this.insertSectionBefore(this.editor.post.sections, newSection, null);\n } else {\n this._replaceSection(section, [newSection]);\n }\n }\n }, {\n key: 'moveSectionBefore',\n value: function moveSectionBefore(collection, renderedSection, beforeSection) {\n var newSection = renderedSection.clone();\n this.removeSection(renderedSection);\n this.insertSectionBefore(collection, newSection, beforeSection);\n return newSection;\n }\n\n /**\n * @param {Section} section A section that is already in DOM\n * @public\n */\n }, {\n key: 'moveSectionUp',\n value: function moveSectionUp(renderedSection) {\n var isFirst = !renderedSection.prev;\n if (isFirst) {\n return renderedSection;\n }\n\n var collection = renderedSection.parent.sections;\n var beforeSection = renderedSection.prev;\n return this.moveSectionBefore(collection, renderedSection, beforeSection);\n }\n\n /**\n * @param {Section} section A section that is already in DOM\n * @public\n */\n }, {\n key: 'moveSectionDown',\n value: function moveSectionDown(renderedSection) {\n var isLast = !renderedSection.next;\n if (isLast) {\n return renderedSection;\n }\n\n var beforeSection = renderedSection.next.next;\n var collection = renderedSection.parent.sections;\n return this.moveSectionBefore(collection, renderedSection, beforeSection);\n }\n\n /**\n * Insert an array of markers at the given position. If the position is in\n * a non-markerable section (like a card section), this method throws an error.\n *\n * @param {Position} position\n * @param {Marker[]} markers\n * @return {Position} The position that represents the end of the inserted markers.\n * @public\n */\n }, {\n key: 'insertMarkers',\n value: function insertMarkers(position, markers) {\n var _this9 = this;\n\n var section = position.section;\n var offset = position.offset;\n\n (0, _mobiledocKitUtilsAssert['default'])('Cannot insert markers at non-markerable position', section.isMarkerable);\n\n var edit = section.splitMarkerAtOffset(offset);\n edit.removed.forEach(function (marker) {\n return _this9._scheduleForRemoval(marker);\n });\n\n var prevMarker = section.markerBeforeOffset(offset);\n markers.forEach(function (marker) {\n section.markers.insertAfter(marker, prevMarker);\n offset += marker.length;\n prevMarker = marker;\n });\n\n this._coalesceMarkers(section);\n this._markDirty(section);\n\n var nextPosition = section.toPosition(offset);\n this.setRange(nextPosition);\n return nextPosition;\n }\n\n /**\n * Inserts text with the given markups, ignoring the existing markups at\n * the position, if any.\n *\n * @param {Position} position\n * @param {String} text\n * @param {Markup[]} markups\n * @return {Position} position at the end of the inserted text\n */\n }, {\n key: 'insertTextWithMarkup',\n value: function insertTextWithMarkup(position, text) {\n var markups = arguments.length <= 2 || arguments[2] === undefined ? [] : arguments[2];\n var section = position.section;\n\n if (!section.isMarkerable) {\n return;\n }\n var marker = this.builder.createMarker(text, markups);\n return this.insertMarkers(position, [marker]);\n }\n\n /**\n * Insert the text at the given position\n * Inherits the markups already at that position, if any.\n *\n * @param {Position} position\n * @param {String} text\n * @return {Position} position at the end of the inserted text.\n */\n }, {\n key: 'insertText',\n value: function insertText(position, text) {\n var section = position.section;\n\n if (!section.isMarkerable) {\n return;\n }\n var markups = position.marker && position.marker.markups;\n markups = markups || [];\n return this.insertTextWithMarkup(position, text, markups);\n }\n }, {\n key: '_replaceSection',\n value: function _replaceSection(section, newSections) {\n var _this10 = this;\n\n var nextSection = section.next;\n var collection = section.parent.sections;\n\n var nextNewSection = newSections[0];\n if (nextNewSection.isMarkupSection && section.isListItem) {\n // put the new section after the ListSection (section.parent)\n // instead of after the ListItem\n collection = section.parent.parent.sections;\n nextSection = section.parent.next;\n }\n\n newSections.forEach(function (s) {\n return _this10.insertSectionBefore(collection, s, nextSection);\n });\n this.removeSection(section);\n }\n\n /**\n * Given a markerRange (for example `editor.range`) mark all markers\n * inside it as a given markup. The markup must be provided as a post\n * abstract node.\n *\n * Usage:\n *\n * let range = editor.range;\n * let strongMarkup = editor.builder.createMarkup('strong');\n * editor.run((postEditor) => {\n * postEditor.addMarkupToRange(range, strongMarkup);\n * });\n * // Will result some markers possibly being split, and the markup\n * // being applied to all markers between the split.\n *\n * @param {Range} range\n * @param {Markup} markup A markup post abstract node\n * @public\n */\n }, {\n key: 'addMarkupToRange',\n value: function addMarkupToRange(range, markup) {\n var _this11 = this;\n\n if (range.isCollapsed) {\n return;\n }\n\n var markers = this.splitMarkers(range);\n if (markers.length) {\n (function () {\n // We insert the new markup at a consistent index across the range.\n // If we just push on the end of the list, it can end up in different positions\n // of the markup stack. This results in unnecessary closing and re-opening of\n // the markup each time it changes position.\n // If we just push it at the beginning of the list, this causes unnecessary closing\n // and re-opening of surrounding tags.\n // So, we look for any tags open across the whole range, and push into the stack\n // at the end of those.\n // Prompted by https://github.com/bustle/mobiledoc-kit/issues/360\n\n var markupsOpenAcrossRange = (0, _mobiledocKitUtilsArrayUtils.reduce)(markers, function (soFar, marker) {\n return (0, _mobiledocKitUtilsArrayUtils.commonItems)(soFar, marker.markups);\n }, markers[0].markups);\n var indexToInsert = markupsOpenAcrossRange.length;\n\n markers.forEach(function (marker) {\n marker.addMarkupAtIndex(markup, indexToInsert);\n _this11._markDirty(marker);\n });\n })();\n }\n }\n\n /**\n * Given a markerRange (for example `editor.range`) remove the given\n * markup from all contained markers.\n *\n * Usage:\n * ```\n * let { range } = editor;\n * let markup = markerRange.headMarker.markups[0];\n * editor.run(postEditor => {\n * postEditor.removeMarkupFromRange(range, markup);\n * });\n * // Will result in some markers possibly being split, and the markup\n * // being removed from all markers between the split.\n * ```\n * @param {Range} range Object with offsets\n * @param {Markup|Function} markupOrCallback A markup post abstract node or\n * a function that returns true when passed a markup that should be removed\n * @private\n */\n }, {\n key: 'removeMarkupFromRange',\n value: function removeMarkupFromRange(range, markupOrMarkupCallback) {\n var _this12 = this;\n\n if (range.isCollapsed) {\n return;\n }\n\n this.splitMarkers(range).forEach(function (marker) {\n marker.removeMarkup(markupOrMarkupCallback);\n _this12._markDirty(marker);\n });\n }\n\n /**\n * Toggle the given markup in the given range (or at the position given). If the range/position\n * has the markup, the markup will be removed. If nothing in the range/position\n * has the markup, the markup will be added to everything in the range/position.\n *\n * Usage:\n * ```\n * // Remove any 'strong' markup if it exists in the selection, otherwise\n * // make it all 'strong'\n * editor.run(postEditor => postEditor.toggleMarkup('strong'));\n *\n * // add/remove a link to 'bustle.com' to the selection\n * editor.run(postEditor => {\n * const linkMarkup = postEditor.builder.createMarkup('a', {href: 'http://bustle.com'});\n * postEditor.toggleMarkup(linkMarkup);\n * });\n * ```\n * @param {Markup|String} markupOrString Either a markup object created using\n * the builder (useful when adding a markup with attributes, like an 'a' markup),\n * or, if a string, the tag name of the markup (e.g. 'strong', 'em') to toggle.\n * @param {Range|Position} range in which to toggle. Defaults to current editor range.\n * @public\n */\n }, {\n key: 'toggleMarkup',\n value: function toggleMarkup(markupOrMarkupString) {\n var range = arguments.length <= 1 || arguments[1] === undefined ? this._range : arguments[1];\n\n range = (0, _mobiledocKitUtilsToRange['default'])(range);\n var markup = typeof markupOrMarkupString === 'string' ? this.builder.createMarkup(markupOrMarkupString) : markupOrMarkupString;\n\n var hasMarkup = this.editor.detectMarkupInRange(range, markup.tagName);\n // FIXME: This implies only a single markup in a range. This may not be\n // true for links (which are not the same object instance like multiple\n // strong tags would be).\n if (hasMarkup) {\n this.removeMarkupFromRange(range, hasMarkup);\n } else {\n this.addMarkupToRange(range, markup);\n }\n\n this.setRange(range);\n }\n\n /**\n * Toggles the tagName of the active section or sections in the given range/position.\n * If every section has the tag name, they will all be reset to default sections.\n * Otherwise, every section will be changed to the requested type\n *\n * @param {String} sectionTagName A valid markup section or\n * list section tag name (e.g. 'blockquote', 'h2', 'ul')\n * @param {Range|Position} range The range over which to toggle.\n * Defaults to the current editor range.\n * @public\n */\n }, {\n key: 'toggleSection',\n value: function toggleSection(sectionTagName) {\n var _this13 = this;\n\n var range = arguments.length <= 1 || arguments[1] === undefined ? this._range : arguments[1];\n\n range = (0, _mobiledocKitUtilsToRange['default'])(range);\n\n sectionTagName = (0, _mobiledocKitUtilsDomUtils.normalizeTagName)(sectionTagName);\n var post = this.editor.post;\n\n var nextRange = range;\n\n var everySectionHasTagName = true;\n post.walkMarkerableSections(range, function (section) {\n if (!_this13._isSameSectionType(section, sectionTagName)) {\n everySectionHasTagName = false;\n }\n });\n\n var tagName = everySectionHasTagName ? 'p' : sectionTagName;\n var firstChanged = undefined;\n post.walkMarkerableSections(range, function (section) {\n var changedSection = _this13.changeSectionTagName(section, tagName);\n firstChanged = firstChanged || changedSection;\n });\n\n if (firstChanged) {\n nextRange = firstChanged.headPosition().toRange();\n }\n this.setRange(nextRange);\n }\n }, {\n key: '_isSameSectionType',\n value: function _isSameSectionType(section, sectionTagName) {\n return section.isListItem ? section.parent.tagName === sectionTagName : section.tagName === sectionTagName;\n }\n\n /**\n * @param {Markerable} section\n * @private\n */\n }, {\n key: 'changeSectionTagName',\n value: function changeSectionTagName(section, newTagName) {\n (0, _mobiledocKitUtilsAssert['default'])('Cannot pass non-markerable section to `changeSectionTagName`', section.isMarkerable);\n\n if (isListSectionTagName(newTagName)) {\n return this._changeSectionToListItem(section, newTagName);\n } else if (section.isListItem) {\n return this._changeSectionFromListItem(section, newTagName);\n } else {\n section.tagName = newTagName;\n this._markDirty(section);\n return section;\n }\n }\n\n /**\n * Splits the item at the position given.\n * If the position is at the start or end of the item, the pre- or post-item\n * will contain a single empty (\"\") marker.\n * @param {ListItem} item\n * @param {Position} position\n * @return {Array} the pre-item and post-item on either side of the split\n * @private\n */\n }, {\n key: '_splitListItem',\n value: function _splitListItem(item, position) {\n var section = position.section;\n var offset = position.offset;\n\n (0, _mobiledocKitUtilsAssert['default'])('Cannot split list item at position that does not include item', item === section);\n\n item.splitMarkerAtOffset(offset);\n var prevMarker = item.markerBeforeOffset(offset);\n var preItem = this.builder.createListItem(),\n postItem = this.builder.createListItem();\n\n var currentItem = preItem;\n item.markers.forEach(function (marker) {\n currentItem.markers.append(marker.clone());\n if (marker === prevMarker) {\n currentItem = postItem;\n }\n });\n this._replaceSection(item, [preItem, postItem]);\n return [preItem, postItem];\n }\n\n /**\n * Splits the list at the position given.\n * @return {Array} pre-split list and post-split list, either of which could\n * be blank (0-item list) if the position is at the start or end of the list.\n *\n * Note: Contiguous list sections will be joined in the before_complete queue\n * of the postEditor.\n *\n * @private\n */\n }, {\n key: '_splitListAtPosition',\n value: function _splitListAtPosition(list, position) {\n (0, _mobiledocKitUtilsAssert['default'])('Cannot split list at position not in list', position.section.parent === list);\n\n var positionIsMiddle = !position.isHead() && !position.isTail();\n if (positionIsMiddle) {\n var item = position.section;\n\n var _splitListItem3 = // jshint ignore:line\n this._splitListItem(item, position);\n\n var _splitListItem32 = _slicedToArray(_splitListItem3, 2);\n\n var pre = _splitListItem32[0];\n var post = _splitListItem32[1];\n\n position = pre.tailPosition();\n }\n\n var preList = this.builder.createListSection(list.tagName);\n var postList = this.builder.createListSection(list.tagName);\n\n var preItem = position.section;\n var currentList = preList;\n list.items.forEach(function (item) {\n // If this item matches the start item and the position is at its start,\n // it should be appended to the postList instead of the preList\n if (item === preItem && position.isEqual(item.headPosition())) {\n currentList = postList;\n }\n currentList.items.append(item.clone());\n // If we just appended the preItem, append the remaining items to the postList\n if (item === preItem) {\n currentList = postList;\n }\n });\n\n this._replaceSection(list, [preList, postList]);\n return [preList, postList];\n }\n\n /**\n * @return Array of [prev, mid, next] lists. `prev` and `next` can\n * be blank, depending on the position of `item`. `mid` will always\n * be a 1-item list containing `item`. `prev` and `next` will be\n * removed in the before_complete queue if they are blank\n * (and still attached).\n *\n * @private\n */\n }, {\n key: '_splitListAtItem',\n value: function _splitListAtItem(list, item) {\n var _this14 = this;\n\n var next = list;\n var prev = this.builder.createListSection(next.tagName);\n var mid = this.builder.createListSection(next.tagName);\n\n var addToPrev = true;\n // must turn the LinkedList into an array so that we can remove items\n // as we iterate through it\n var items = next.items.toArray();\n items.forEach(function (i) {\n var listToAppend = undefined;\n if (i === item) {\n addToPrev = false;\n listToAppend = mid;\n } else if (addToPrev) {\n listToAppend = prev;\n } else {\n return; // break after iterating prev and mid parts of the list\n }\n listToAppend.join(i);\n _this14.removeSection(i);\n });\n var found = !addToPrev;\n (0, _mobiledocKitUtilsAssert['default'])('Cannot split list at item that is not present in the list', found);\n\n var collection = this.editor.post.sections;\n this.insertSectionBefore(collection, mid, next);\n this.insertSectionBefore(collection, prev, mid);\n\n // Remove possibly blank prev/next lists\n this.addCallback(CALLBACK_QUEUES.BEFORE_COMPLETE, function () {\n [prev, next].forEach(function (_list) {\n var isAttached = !!_list.parent;\n if (_list.isBlank && isAttached) {\n _this14.removeSection(_list);\n }\n });\n });\n\n return [prev, mid, next];\n }\n }, {\n key: '_changeSectionFromListItem',\n value: function _changeSectionFromListItem(section, newTagName) {\n (0, _mobiledocKitUtilsAssert['default'])('Must pass list item to `_changeSectionFromListItem`', section.isListItem);\n\n var listSection = section.parent;\n var markupSection = this.builder.createMarkupSection(newTagName);\n markupSection.join(section);\n\n var _splitListAtItem2 = this._splitListAtItem(listSection, section);\n\n var _splitListAtItem22 = _slicedToArray(_splitListAtItem2, 3);\n\n var prev = _splitListAtItem22[0];\n var mid = _splitListAtItem22[1];\n var next = _splitListAtItem22[2];\n // jshint ignore:line\n this.replaceSection(mid, markupSection);\n return markupSection;\n }\n }, {\n key: '_changeSectionToListItem',\n value: function _changeSectionToListItem(section, newTagName) {\n var isAlreadyCorrectListItem = section.isListItem && section.parent.tagName === newTagName;\n\n if (isAlreadyCorrectListItem) {\n return section;\n }\n\n var listSection = this.builder.createListSection(newTagName);\n listSection.join(section);\n\n var sectionToReplace = undefined;\n if (section.isListItem) {\n var _splitListAtItem3 = this._splitListAtItem(section.parent, section);\n\n var _splitListAtItem32 = _slicedToArray(_splitListAtItem3, 3);\n\n var prev = _splitListAtItem32[0];\n var mid = _splitListAtItem32[1];\n var next = _splitListAtItem32[2];\n // jshint ignore:line\n sectionToReplace = mid;\n } else {\n sectionToReplace = section;\n }\n this.replaceSection(sectionToReplace, listSection);\n return listSection;\n }\n\n /**\n * Insert a given section before another one, updating the post abstract\n * and the rendered UI.\n *\n * Usage:\n * ```\n * let markerRange = editor.range;\n * let sectionWithCursor = markerRange.headMarker.section;\n * let section = editor.builder.createCardSection('my-image');\n * let collection = sectionWithCursor.parent.sections;\n * editor.run((postEditor) => {\n * postEditor.insertSectionBefore(collection, section, sectionWithCursor);\n * });\n * ```\n * @param {LinkedList} collection The list of sections to insert into\n * @param {Object} section The new section\n * @param {Object} beforeSection Optional The section \"before\" is relative to,\n * if falsy the new section will be appended to the collection\n * @public\n */\n }, {\n key: 'insertSectionBefore',\n value: function insertSectionBefore(collection, section, beforeSection) {\n collection.insertBefore(section, beforeSection);\n this._markDirty(section.parent);\n }\n\n /**\n * Insert the given section after the current active section, or, if no\n * section is active, at the end of the document.\n * @param {Section} section\n * @public\n */\n }, {\n key: 'insertSection',\n value: function insertSection(section) {\n var activeSection = this.editor.activeSection;\n var nextSection = activeSection && activeSection.next;\n\n var collection = this.editor.post.sections;\n this.insertSectionBefore(collection, section, nextSection);\n }\n\n /**\n * Insert the given section at the end of the document.\n * @param {Section} section\n * @public\n */\n }, {\n key: 'insertSectionAtEnd',\n value: function insertSectionAtEnd(section) {\n this.insertSectionBefore(this.editor.post.sections, section, null);\n }\n\n /**\n * Insert the `post` at the given position in the editor's post.\n * @param {Position} position\n * @param {Post} post\n * @private\n */\n }, {\n key: 'insertPost',\n value: function insertPost(position, newPost) {\n var post = this.editor.post;\n var inserter = new _mobiledocKitEditorPostPostInserter['default'](this, post);\n var nextPosition = inserter.insert(position, newPost);\n return nextPosition;\n }\n\n /**\n * Remove a given section from the post abstract and the rendered UI.\n *\n * Usage:\n * ```\n * let { range } = editor;\n * let sectionWithCursor = range.head.section;\n * editor.run((postEditor) => {\n * postEditor.removeSection(sectionWithCursor);\n * });\n * ```\n * @param {Object} section The section to remove\n * @public\n */\n }, {\n key: 'removeSection',\n value: function removeSection(section) {\n var parent = section.parent;\n this._scheduleForRemoval(section);\n parent.sections.remove(section);\n\n if (parent.isListSection) {\n this._scheduleListRemovalIfEmpty(parent);\n }\n }\n }, {\n key: 'removeAllSections',\n value: function removeAllSections() {\n var _this15 = this;\n\n this.editor.post.sections.toArray().forEach(function (section) {\n _this15.removeSection(section);\n });\n }\n }, {\n key: 'migrateSectionsFromPost',\n value: function migrateSectionsFromPost(post) {\n var _this16 = this;\n\n post.sections.toArray().forEach(function (section) {\n post.sections.remove(section);\n _this16.insertSectionBefore(_this16.editor.post.sections, section, null);\n });\n }\n }, {\n key: '_scheduleListRemovalIfEmpty',\n value: function _scheduleListRemovalIfEmpty(listSection) {\n var _this17 = this;\n\n this.addCallback(CALLBACK_QUEUES.BEFORE_COMPLETE, function () {\n // if the list is attached and blank after we do other rendering stuff,\n // remove it\n var isAttached = !!listSection.parent;\n if (isAttached && listSection.isBlank) {\n _this17.removeSection(listSection);\n }\n });\n }\n\n /**\n * A method for adding work the deferred queue\n *\n * @param {Function} callback to run during completion\n * @param {Boolean} [once=false] Whether to only schedule the callback once.\n * @public\n */\n }, {\n key: 'schedule',\n value: function schedule(callback) {\n var once = arguments.length <= 1 || arguments[1] === undefined ? false : arguments[1];\n\n (0, _mobiledocKitUtilsAssert['default'])('Work can only be scheduled before a post edit has completed', !this._didComplete);\n if (once) {\n this.addCallbackOnce(CALLBACK_QUEUES.COMPLETE, callback);\n } else {\n this.addCallback(CALLBACK_QUEUES.COMPLETE, callback);\n }\n }\n\n /**\n * A method for adding work the deferred queue. The callback will only\n * be added to the queue once, even if `scheduleOnce` is called multiple times.\n * The function cannot be an anonymous function.\n *\n * @param {Function} callback to run during completion\n * @public\n */\n }, {\n key: 'scheduleOnce',\n value: function scheduleOnce(callback) {\n this.schedule(callback, true);\n }\n\n /**\n * Add a rerender job to the queue\n *\n * @public\n */\n }, {\n key: 'scheduleRerender',\n value: function scheduleRerender() {\n this.scheduleOnce(this._rerender);\n }\n\n /**\n * Schedule a notification that the post has been changed.\n * The notification will result in the editor firing its `postDidChange`\n * hook after the postEditor completes its work (at the end of {@link Editor#run}).\n *\n * @public\n */\n }, {\n key: 'scheduleDidUpdate',\n value: function scheduleDidUpdate() {\n this.scheduleOnce(this._postDidChange);\n }\n }, {\n key: 'scheduleAfterRender',\n value: function scheduleAfterRender(callback) {\n var once = arguments.length <= 1 || arguments[1] === undefined ? false : arguments[1];\n\n if (once) {\n this.addCallbackOnce(CALLBACK_QUEUES.AFTER_COMPLETE, callback);\n } else {\n this.addCallback(CALLBACK_QUEUES.AFTER_COMPLETE, callback);\n }\n }\n\n /**\n * Flush any work on the queue. {@link Editor#run} calls this method; it\n * should not be called directly.\n *\n * @private\n */\n }, {\n key: 'complete',\n value: function complete() {\n (0, _mobiledocKitUtilsAssert['default'])('Post editing can only be completed once', !this._didComplete);\n\n this.runCallbacks(CALLBACK_QUEUES.BEFORE_COMPLETE);\n this._didComplete = true;\n this.runCallbacks(CALLBACK_QUEUES.COMPLETE);\n this.runCallbacks(CALLBACK_QUEUES.AFTER_COMPLETE);\n }\n }, {\n key: 'undoLastChange',\n value: function undoLastChange() {\n this.editor._editHistory.stepBackward(this);\n }\n }, {\n key: 'redoLastChange',\n value: function redoLastChange() {\n this.editor._editHistory.stepForward(this);\n }\n }, {\n key: 'cancelSnapshot',\n value: function cancelSnapshot() {\n this._shouldCancelSnapshot = true;\n }\n }]);\n\n return PostEditor;\n })();\n\n exports['default'] = PostEditor;\n});","define('mobiledoc-kit/editor/post/post-inserter', ['exports', 'mobiledoc-kit/utils/assert', 'mobiledoc-kit/models/types'], function (exports, _mobiledocKitUtilsAssert, _mobiledocKitModelsTypes) {\n 'use strict';\n\n var _slicedToArray = (function () { function sliceIterator(arr, i) { var _arr = []; var _n = true; var _d = false; var _e = undefined; try { for (var _i = arr[Symbol.iterator](), _s; !(_n = (_s = _i.next()).done); _n = true) { _arr.push(_s.value); if (i && _arr.length === i) break; } } catch (err) { _d = true; _e = err; } finally { try { if (!_n && _i['return']) _i['return'](); } finally { if (_d) throw _e; } } return _arr; } return function (arr, i) { if (Array.isArray(arr)) { return arr; } else if (Symbol.iterator in Object(arr)) { return sliceIterator(arr, i); } else { throw new TypeError('Invalid attempt to destructure non-iterable instance'); } }; })();\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n var MARKERABLE = 'markerable',\n NESTED_MARKERABLE = 'nested_markerable',\n NON_MARKERABLE = 'non_markerable';\n\n var Visitor = (function () {\n function Visitor(inserter, cursorPosition) {\n _classCallCheck(this, Visitor);\n\n var postEditor = inserter.postEditor;\n var post = inserter.post;\n\n this.postEditor = postEditor;\n this._post = post;\n this.cursorPosition = cursorPosition;\n this.builder = this.postEditor.builder;\n\n this._hasInsertedFirstLeafSection = false;\n }\n\n _createClass(Visitor, [{\n key: 'visit',\n value: function visit(node) {\n var method = node.type;\n (0, _mobiledocKitUtilsAssert['default'])('Cannot visit node of type ' + node.type, !!this[method]);\n this[method](node);\n }\n }, {\n key: '_canMergeSection',\n value: function _canMergeSection(section) {\n if (this._hasInsertedFirstLeafSection) {\n return false;\n } else {\n return this._isMarkerable && section.isMarkerable;\n }\n }\n }, {\n key: _mobiledocKitModelsTypes.POST_TYPE,\n value: function value(node) {\n var _this = this;\n\n if (this.cursorSection.isBlank && !this._isNested) {\n // replace blank section with entire post\n var newSections = node.sections.map(function (s) {\n return s.clone();\n });\n this._replaceSection(this.cursorSection, newSections);\n } else {\n node.sections.forEach(function (section) {\n return _this.visit(section);\n });\n }\n }\n }, {\n key: _mobiledocKitModelsTypes.MARKUP_SECTION_TYPE,\n value: function value(node) {\n this[MARKERABLE](node);\n }\n }, {\n key: _mobiledocKitModelsTypes.LIST_SECTION_TYPE,\n value: function value(node) {\n var _this2 = this;\n\n var hasNext = !!node.next;\n node.items.forEach(function (item) {\n return _this2.visit(item);\n });\n\n if (this._isNested && hasNext) {\n this._breakNestedAtCursor();\n }\n }\n }, {\n key: _mobiledocKitModelsTypes.LIST_ITEM_TYPE,\n value: function value(node) {\n this[NESTED_MARKERABLE](node);\n }\n }, {\n key: _mobiledocKitModelsTypes.CARD_TYPE,\n value: function value(node) {\n this[NON_MARKERABLE](node);\n }\n }, {\n key: _mobiledocKitModelsTypes.IMAGE_SECTION_TYPE,\n value: function value(node) {\n this[NON_MARKERABLE](node);\n }\n }, {\n key: NON_MARKERABLE,\n value: function value(section) {\n if (this._isNested) {\n this._breakNestedAtCursor();\n } else if (!this.cursorSection.isBlank) {\n this._breakAtCursor();\n }\n\n this._insertLeafSection(section);\n }\n }, {\n key: MARKERABLE,\n value: function value(section) {\n if (this._canMergeSection(section)) {\n this._mergeSection(section);\n } else if (this._isNested && this._isMarkerable) {\n // If we are attaching a markerable section to a list item,\n // insert a linebreak then merge the section onto the resulting blank list item\n this._breakAtCursor();\n\n // Advance the cursor to the head of the blank list item\n var nextPosition = this.cursorSection.next.headPosition();\n this.cursorPosition = nextPosition;\n\n // Merge this section onto the list item\n this._mergeSection(section);\n } else {\n this._breakAtCursor();\n this._insertLeafSection(section);\n }\n }\n }, {\n key: NESTED_MARKERABLE,\n value: function value(section) {\n if (this._canMergeSection(section)) {\n this._mergeSection(section);\n return;\n }\n\n section = this._isNested ? section : this._wrapNestedSection(section);\n this._breakAtCursor();\n this._insertLeafSection(section);\n }\n\n // break out of a nested cursor position\n }, {\n key: '_breakNestedAtCursor',\n value: function _breakNestedAtCursor() {\n (0, _mobiledocKitUtilsAssert['default'])('Cannot call _breakNestedAtCursor if not nested', this._isNested);\n\n var parent = this.cursorSection.parent;\n var cursorAtEndOfList = this.cursorPosition.isEqual(parent.tailPosition());\n\n if (cursorAtEndOfList) {\n var blank = this.builder.createMarkupSection();\n this._insertSectionAfter(blank, parent);\n } else {\n var _breakListAtCursor2 = this._breakListAtCursor();\n\n var _breakListAtCursor22 = _slicedToArray(_breakListAtCursor2, 3);\n\n var pre = _breakListAtCursor22[0];\n var blank = _breakListAtCursor22[1];\n var post = _breakListAtCursor22[2];\n // jshint ignore:line\n this.cursorPosition = blank.tailPosition();\n }\n }\n }, {\n key: '_breakListAtCursor',\n value: function _breakListAtCursor() {\n (0, _mobiledocKitUtilsAssert['default'])('Cannot _splitParentSection if cursor position is not nested', this._isNested);\n\n var list = this.cursorSection.parent,\n position = this.cursorPosition,\n blank = this.builder.createMarkupSection();\n\n var _postEditor$_splitListAtPosition = this.postEditor._splitListAtPosition(list, position);\n\n var _postEditor$_splitListAtPosition2 = _slicedToArray(_postEditor$_splitListAtPosition, 2);\n\n var pre = _postEditor$_splitListAtPosition2[0];\n var post = _postEditor$_splitListAtPosition2[1];\n\n var collection = this._post.sections,\n reference = post;\n this.postEditor.insertSectionBefore(collection, blank, reference);\n return [pre, blank, post];\n }\n }, {\n key: '_wrapNestedSection',\n value: function _wrapNestedSection(section) {\n var tagName = section.parent.tagName;\n var parent = this.builder.createListSection(tagName);\n parent.items.append(section.clone());\n return parent;\n }\n }, {\n key: '_mergeSection',\n value: function _mergeSection(section) {\n (0, _mobiledocKitUtilsAssert['default'])('Can only merge markerable sections', this._isMarkerable && section.isMarkerable);\n this._hasInsertedFirstLeafSection = true;\n\n var markers = section.markers.map(function (m) {\n return m.clone();\n });\n var position = this.postEditor.insertMarkers(this.cursorPosition, markers);\n\n this.cursorPosition = position;\n }\n\n // Can be called to add a line break when in a nested section or a parent\n // section.\n }, {\n key: '_breakAtCursor',\n value: function _breakAtCursor() {\n if (this.cursorSection.isBlank) {\n return;\n } else if (this._isMarkerable) {\n this._breakMarkerableAtCursor();\n } else {\n this._breakNonMarkerableAtCursor();\n }\n }\n\n // Inserts a blank section before/after the cursor,\n // depending on cursor position.\n }, {\n key: '_breakNonMarkerableAtCursor',\n value: function _breakNonMarkerableAtCursor() {\n var collection = this._post.sections,\n blank = this.builder.createMarkupSection(),\n reference = this.cursorPosition.isHead() ? this.cursorSection : this.cursorSection.next;\n this.postEditor.insertSectionBefore(collection, blank, reference);\n this.cursorPosition = blank.tailPosition();\n }\n }, {\n key: '_breakMarkerableAtCursor',\n value: function _breakMarkerableAtCursor() {\n var _postEditor$splitSection = // jshint ignore:line\n this.postEditor.splitSection(this.cursorPosition);\n\n var _postEditor$splitSection2 = _slicedToArray(_postEditor$splitSection, 2);\n\n var pre = _postEditor$splitSection2[0];\n var post = _postEditor$splitSection2[1];\n\n this.cursorPosition = pre.tailPosition();\n }\n }, {\n key: '_replaceSection',\n value: function _replaceSection(section, newSections) {\n var _this3 = this;\n\n (0, _mobiledocKitUtilsAssert['default'])('Cannot replace section that does not have parent.sections', section.parent && section.parent.sections);\n (0, _mobiledocKitUtilsAssert['default'])('Must pass enumerable to _replaceSection', !!newSections.forEach);\n\n var collection = section.parent.sections;\n var reference = section.next;\n this.postEditor.removeSection(section);\n newSections.forEach(function (section) {\n _this3.postEditor.insertSectionBefore(collection, section, reference);\n });\n var lastSection = newSections[newSections.length - 1];\n\n this.cursorPosition = lastSection.tailPosition();\n }\n }, {\n key: '_insertSectionBefore',\n value: function _insertSectionBefore(section, reference) {\n var collection = this.cursorSection.parent.sections;\n this.postEditor.insertSectionBefore(collection, section, reference);\n\n this.cursorPosition = section.tailPosition();\n }\n\n // Insert a section after the parent section.\n // E.g., add a markup section after a list section\n }, {\n key: '_insertSectionAfter',\n value: function _insertSectionAfter(section, parent) {\n (0, _mobiledocKitUtilsAssert['default'])('Cannot _insertSectionAfter nested section', !parent.isNested);\n var reference = parent.next;\n var collection = this._post.sections;\n this.postEditor.insertSectionBefore(collection, section, reference);\n this.cursorPosition = section.tailPosition();\n }\n }, {\n key: '_insertLeafSection',\n value: function _insertLeafSection(section) {\n (0, _mobiledocKitUtilsAssert['default'])('Can only _insertLeafSection when cursor is at end of section', this.cursorPosition.isTail());\n\n this._hasInsertedFirstLeafSection = true;\n section = section.clone();\n\n if (this.cursorSection.isBlank) {\n (0, _mobiledocKitUtilsAssert['default'])('Cannot insert leaf non-markerable section when cursor is nested', !(section.isMarkerable && this._isNested));\n this._replaceSection(this.cursorSection, [section]);\n } else if (this.cursorSection.next && this.cursorSection.next.isBlank) {\n this._replaceSection(this.cursorSection.next, [section]);\n } else {\n var reference = this.cursorSection.next;\n this._insertSectionBefore(section, reference);\n }\n }\n }, {\n key: 'cursorPosition',\n get: function get() {\n return this._cursorPosition;\n },\n set: function set(position) {\n this._cursorPosition = position;\n this.postEditor.setRange(position);\n }\n }, {\n key: '_isMarkerable',\n get: function get() {\n return this.cursorSection.isMarkerable;\n }\n }, {\n key: 'cursorSection',\n get: function get() {\n return this.cursorPosition.section;\n }\n }, {\n key: 'cursorOffset',\n get: function get() {\n return this.cursorPosition.offset;\n }\n }, {\n key: '_isNested',\n get: function get() {\n return this.cursorSection.isNested;\n }\n }]);\n\n return Visitor;\n })();\n\n var Inserter = (function () {\n function Inserter(postEditor, post) {\n _classCallCheck(this, Inserter);\n\n this.postEditor = postEditor;\n this.post = post;\n }\n\n _createClass(Inserter, [{\n key: 'insert',\n value: function insert(cursorPosition, newPost) {\n var visitor = new Visitor(this, cursorPosition);\n visitor.visit(newPost);\n return visitor.cursorPosition;\n }\n }]);\n\n return Inserter;\n })();\n\n exports['default'] = Inserter;\n});","define(\"mobiledoc-kit/editor/selection-change-observer\", [\"exports\"], function (exports) {\n \"use strict\";\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if (\"value\" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError(\"Cannot call a class as a function\"); } }\n\n var instance = undefined;\n\n var SelectionChangeObserver = (function () {\n function SelectionChangeObserver() {\n _classCallCheck(this, SelectionChangeObserver);\n\n this.started = false;\n this.listeners = [];\n this.selection = {};\n }\n\n _createClass(SelectionChangeObserver, [{\n key: \"addListener\",\n value: function addListener(listener) {\n if (this.listeners.indexOf(listener) === -1) {\n this.listeners.push(listener);\n this.start();\n }\n }\n }, {\n key: \"removeListener\",\n value: function removeListener(listener) {\n var index = this.listeners.indexOf(listener);\n if (index !== -1) {\n this.listeners.splice(index, 1);\n if (this.listeners.length === 0) {\n this.stop();\n }\n }\n }\n }, {\n key: \"start\",\n value: function start() {\n if (this.started) {\n return;\n }\n this.started = true;\n\n this.poll();\n }\n }, {\n key: \"stop\",\n value: function stop() {\n this.started = false;\n this.selection = {};\n }\n }, {\n key: \"notifyListeners\",\n value: function notifyListeners() /* newSelection, prevSelection */{\n var _arguments = arguments;\n\n this.listeners.forEach(function (listener) {\n listener.selectionDidChange.apply(listener, _arguments);\n });\n }\n }, {\n key: \"destroy\",\n value: function destroy() {\n this.stop();\n this.listeners = [];\n }\n }, {\n key: \"getSelection\",\n value: function getSelection() {\n var selection = window.getSelection();\n var anchorNode = selection.anchorNode;\n var focusNode = selection.focusNode;\n var anchorOffset = selection.anchorOffset;\n var focusOffset = selection.focusOffset;\n\n return { anchorNode: anchorNode, focusNode: focusNode, anchorOffset: anchorOffset, focusOffset: focusOffset };\n }\n }, {\n key: \"poll\",\n value: function poll() {\n var _this = this;\n\n if (this.started) {\n this.update();\n this.runNext(function () {\n return _this.poll();\n });\n }\n }\n }, {\n key: \"runNext\",\n value: function runNext(fn) {\n window.requestAnimationFrame(fn);\n }\n }, {\n key: \"update\",\n value: function update() {\n var prevSelection = this.selection;\n var curSelection = this.getSelection();\n if (!this.selectionIsEqual(prevSelection, curSelection)) {\n this.selection = curSelection;\n this.notifyListeners(curSelection, prevSelection);\n }\n }\n }, {\n key: \"selectionIsEqual\",\n value: function selectionIsEqual(s1, s2) {\n return s1.anchorNode === s2.anchorNode && s1.anchorOffset === s2.anchorOffset && s1.focusNode === s2.focusNode && s1.focusOffset === s2.focusOffset;\n }\n }], [{\n key: \"getInstance\",\n value: function getInstance() {\n if (!instance) {\n instance = new SelectionChangeObserver();\n }\n return instance;\n }\n }, {\n key: \"addListener\",\n value: function addListener(listener) {\n SelectionChangeObserver.getInstance().addListener(listener);\n }\n }, {\n key: \"removeListener\",\n value: function removeListener(listener) {\n SelectionChangeObserver.getInstance().removeListener(listener);\n }\n }]);\n\n return SelectionChangeObserver;\n })();\n\n exports[\"default\"] = SelectionChangeObserver;\n});","define('mobiledoc-kit/editor/selection-manager', ['exports', 'mobiledoc-kit/editor/selection-change-observer'], function (exports, _mobiledocKitEditorSelectionChangeObserver) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n var SelectionManager = (function () {\n function SelectionManager(editor, callback) {\n _classCallCheck(this, SelectionManager);\n\n this.editor = editor;\n this.callback = callback;\n this.started = false;\n }\n\n _createClass(SelectionManager, [{\n key: 'start',\n value: function start() {\n if (this.started) {\n return;\n }\n\n _mobiledocKitEditorSelectionChangeObserver['default'].addListener(this);\n this.started = true;\n }\n }, {\n key: 'stop',\n value: function stop() {\n this.started = false;\n _mobiledocKitEditorSelectionChangeObserver['default'].removeListener(this);\n }\n }, {\n key: 'destroy',\n value: function destroy() {\n this.stop();\n }\n }, {\n key: 'selectionDidChange',\n value: function selectionDidChange() {\n if (this.started) {\n this.callback.apply(this, arguments);\n }\n }\n }]);\n\n return SelectionManager;\n })();\n\n exports['default'] = SelectionManager;\n});","define('mobiledoc-kit/editor/text-input-handler', ['exports', 'mobiledoc-kit/utils/string-utils', 'mobiledoc-kit/utils/assert', 'mobiledoc-kit/utils/deprecate'], function (exports, _mobiledocKitUtilsStringUtils, _mobiledocKitUtilsAssert, _mobiledocKitUtilsDeprecate) {\n 'use strict';\n\n var _slicedToArray = (function () { function sliceIterator(arr, i) { var _arr = []; var _n = true; var _d = false; var _e = undefined; try { for (var _i = arr[Symbol.iterator](), _s; !(_n = (_s = _i.next()).done); _n = true) { _arr.push(_s.value); if (i && _arr.length === i) break; } } catch (err) { _d = true; _e = err; } finally { try { if (!_n && _i['return']) _i['return'](); } finally { if (_d) throw _e; } } return _arr; } return function (arr, i) { if (Array.isArray(arr)) { return arr; } else if (Symbol.iterator in Object(arr)) { return sliceIterator(arr, i); } else { throw new TypeError('Invalid attempt to destructure non-iterable instance'); } }; })();\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n var TextInputHandler = (function () {\n function TextInputHandler(editor) {\n _classCallCheck(this, TextInputHandler);\n\n this.editor = editor;\n this._handlers = [];\n }\n\n _createClass(TextInputHandler, [{\n key: 'register',\n value: function register(handler) {\n (0, _mobiledocKitUtilsAssert['default'])('Input Handler is not valid', this._validateHandler(handler));\n this._handlers.push(handler);\n }\n }, {\n key: 'unregister',\n value: function unregister(name) {\n var handlers = this._handlers;\n for (var i = 0; i < handlers.length; i++) {\n if (handlers[i].name === name) {\n handlers.splice(i, 1);\n }\n }\n }\n }, {\n key: 'handle',\n value: function handle(string) {\n var editor = this.editor;\n\n editor.insertText(string);\n\n var matchedHandler = this._findHandler();\n if (matchedHandler) {\n var _matchedHandler = _slicedToArray(matchedHandler, 2);\n\n var handler = _matchedHandler[0];\n var matches = _matchedHandler[1];\n\n handler.run(editor, matches);\n }\n }\n }, {\n key: '_findHandler',\n value: function _findHandler() {\n var _editor$range = this.editor.range;\n var head = _editor$range.head;\n var section = _editor$range.head.section;\n\n var preText = section.textUntil(head);\n\n for (var i = 0; i < this._handlers.length; i++) {\n var handler = this._handlers[i];\n var text = handler.text;\n var match = handler.match;\n\n if (text && (0, _mobiledocKitUtilsStringUtils.endsWith)(preText, text)) {\n return [handler, [text]];\n } else if (match && match.test(preText)) {\n return [handler, match.exec(preText)];\n }\n }\n }\n }, {\n key: '_validateHandler',\n value: function _validateHandler(handler) {\n (0, _mobiledocKitUtilsDeprecate['default'])('Registered input handlers require a \"name\" property so that they can be unregistered', !!handler.name);\n return !!handler.run && ( // has `run`\n !!handler.text || !!handler.match) && // and `text` or `match`\n !(!!handler.text && !!handler.match); // not both `text` and `match`\n }\n }, {\n key: 'destroy',\n value: function destroy() {\n this._handlers = [];\n }\n }]);\n\n return TextInputHandler;\n })();\n\n exports['default'] = TextInputHandler;\n});","define('mobiledoc-kit/editor/text-input-handlers', ['exports'], function (exports) {\n /**\n * Convert section at the editor's cursor position into a list.\n * Does nothing if the cursor position is not at the start of the section,\n * or if the section is already a list item.\n *\n * @param {Editor} editor\n * @param {String} listTagName (\"ul\" or \"ol\")\n * @public\n */\n 'use strict';\n\n exports.replaceWithListSection = replaceWithListSection;\n exports.replaceWithHeaderSection = replaceWithHeaderSection;\n\n function replaceWithListSection(editor, listTagName) {\n var _editor$range = editor.range;\n var head = _editor$range.head;\n var section = _editor$range.head.section;\n\n // Skip if cursor is not at end of section\n if (!head.isTail()) {\n return;\n }\n\n if (section.isListItem) {\n return;\n }\n\n editor.run(function (postEditor) {\n var builder = postEditor.builder;\n\n var item = builder.createListItem();\n var listSection = builder.createListSection(listTagName, [item]);\n\n postEditor.replaceSection(section, listSection);\n postEditor.setRange(listSection.headPosition());\n });\n }\n\n /**\n * Convert section at the editor's cursor position into a header section.\n * Does nothing if the cursor position is not at the start of the section.\n *\n * @param {Editor} editor\n * @param {String} headingTagName (\"h1\",\"h2\",\"h3\")\n * @public\n */\n\n function replaceWithHeaderSection(editor, headingTagName) {\n var _editor$range2 = editor.range;\n var head = _editor$range2.head;\n var section = _editor$range2.head.section;\n\n // Skip if cursor is not at end of section\n if (!head.isTail()) {\n return;\n }\n\n editor.run(function (postEditor) {\n var builder = postEditor.builder;\n\n var newSection = builder.createMarkupSection(headingTagName);\n postEditor.replaceSection(section, newSection);\n postEditor.setRange(newSection.headPosition());\n });\n }\n\n var DEFAULT_TEXT_INPUT_HANDLERS = [{\n name: 'ul',\n // \"* \" -> ul\n match: /^\\* $/,\n run: function run(editor) {\n replaceWithListSection(editor, 'ul');\n }\n }, {\n name: 'ol',\n // \"1\" -> ol, \"1.\" -> ol\n match: /^1\\.? $/,\n run: function run(editor) {\n replaceWithListSection(editor, 'ol');\n }\n }, {\n name: 'heading',\n // \"# \" -> h1, \"## \" -> h2, \"### \" -> h3\n match: /^(#{1,3}) $/,\n run: function run(editor, matches) {\n var capture = matches[1];\n var headingTag = 'h' + capture.length;\n replaceWithHeaderSection(editor, headingTag);\n }\n }];\n exports.DEFAULT_TEXT_INPUT_HANDLERS = DEFAULT_TEXT_INPUT_HANDLERS;\n});","define('mobiledoc-kit/editor/ui', ['exports'], function (exports) {\n /**\n * @module UI\n */\n\n /**\n * @callback promptCallback\n * @param {String} url The URL to pass back to the editor for linking\n * to the selected text.\n */\n\n /**\n * @callback showPrompt\n * @param {String} message The text of the prompt.\n * @param {String} defaultValue The initial URL to display in the prompt.\n * @param {module:UI~promptCallback} callback Once your handler has accepted a URL,\n * it should pass it to `callback` so that the editor may link the\n * selected text.\n */\n\n /**\n * Exposes the core behavior for linking and unlinking text, and allows for\n * customization of the URL input handler.\n * @param {Editor} editor An editor instance to operate on. If a range is selected,\n * either prompt for a URL and add a link or un-link the\n * currently linked text.\n * @param {module:UI~showPrompt} [showPrompt] An optional custom input handler. Defaults\n * to using `window.prompt`.\n * @example\n * let myPrompt = (message, defaultURL, promptCallback) => {\n * let url = window.prompt(\"Overriding the defaults\", \"http://placekitten.com\");\n * promptCallback(url);\n * };\n *\n * editor.registerKeyCommand({\n * str: \"META+K\",\n * run(editor) {\n * toggleLink(editor, myPrompt);\n * }\n * });\n * @public\n */\n\n 'use strict';\n\n exports.toggleLink = toggleLink;\n var defaultShowPrompt = function defaultShowPrompt(message, defaultValue, callback) {\n return callback(window.prompt(message, defaultValue));\n };\n\n function toggleLink(editor) {\n var showPrompt = arguments.length <= 1 || arguments[1] === undefined ? defaultShowPrompt : arguments[1];\n\n if (editor.range.isCollapsed) {\n return;\n }\n\n var selectedText = editor.cursor.selectedText();\n var defaultUrl = '';\n if (selectedText.indexOf('http') !== -1) {\n defaultUrl = selectedText;\n }\n\n var range = editor.range;\n\n var hasLink = editor.detectMarkupInRange(range, 'a');\n\n if (hasLink) {\n editor.run(function (postEditor) {\n return postEditor.toggleMarkup('a');\n });\n } else {\n showPrompt('Enter a URL', defaultUrl, function (url) {\n if (!url) {\n return;\n }\n\n editor.run(function (postEditor) {\n var markup = postEditor.builder.createMarkup('a', { href: url });\n postEditor.toggleMarkup(markup);\n });\n });\n }\n }\n});","define('mobiledoc-kit', ['exports', 'mobiledoc-kit/editor/editor', 'mobiledoc-kit/editor/ui', 'mobiledoc-kit/cards/image', 'mobiledoc-kit/utils/cursor/range', 'mobiledoc-kit/utils/cursor/position', 'mobiledoc-kit/utils/mobiledoc-error', 'mobiledoc-kit/version'], function (exports, _mobiledocKitEditorEditor, _mobiledocKitEditorUi, _mobiledocKitCardsImage, _mobiledocKitUtilsCursorRange, _mobiledocKitUtilsCursorPosition, _mobiledocKitUtilsMobiledocError, _mobiledocKitVersion) {\n 'use strict';\n\n exports.registerGlobal = registerGlobal;\n\n var Mobiledoc = {\n Editor: _mobiledocKitEditorEditor['default'],\n UI: _mobiledocKitEditorUi,\n ImageCard: _mobiledocKitCardsImage['default'],\n Range: _mobiledocKitUtilsCursorRange['default'],\n Position: _mobiledocKitUtilsCursorPosition['default'],\n Error: _mobiledocKitUtilsMobiledocError['default'],\n VERSION: _mobiledocKitVersion['default']\n };\n\n function registerGlobal(global) {\n global.Mobiledoc = Mobiledoc;\n }\n\n exports.Editor = _mobiledocKitEditorEditor['default'];\n exports.UI = _mobiledocKitEditorUi;\n exports.Range = _mobiledocKitUtilsCursorRange['default'];\n exports.Position = _mobiledocKitUtilsCursorPosition['default'];\n exports['default'] = Mobiledoc;\n});","define('mobiledoc-kit/models/_markerable', ['exports', 'mobiledoc-kit/utils/array-utils', 'mobiledoc-kit/utils/set', 'mobiledoc-kit/utils/linked-list', 'mobiledoc-kit/models/_section', 'mobiledoc-kit/utils/assert'], function (exports, _mobiledocKitUtilsArrayUtils, _mobiledocKitUtilsSet, _mobiledocKitUtilsLinkedList, _mobiledocKitModels_section, _mobiledocKitUtilsAssert) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n var _get = function get(_x4, _x5, _x6) { var _again = true; _function: while (_again) { var object = _x4, property = _x5, receiver = _x6; _again = false; if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { _x4 = parent; _x5 = property; _x6 = receiver; _again = true; desc = parent = undefined; continue _function; } } else if ('value' in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } } };\n\n function _toConsumableArray(arr) { if (Array.isArray(arr)) { for (var i = 0, arr2 = Array(arr.length); i < arr.length; i++) arr2[i] = arr[i]; return arr2; } else { return Array.from(arr); } }\n\n function _toArray(arr) { return Array.isArray(arr) ? arr : Array.from(arr); }\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n function _inherits(subClass, superClass) { if (typeof superClass !== 'function' && superClass !== null) { throw new TypeError('Super expression must either be null or a function, not ' + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }\n\n var Markerable = (function (_Section) {\n _inherits(Markerable, _Section);\n\n function Markerable(type, tagName) {\n var _this = this;\n\n var markers = arguments.length <= 2 || arguments[2] === undefined ? [] : arguments[2];\n\n _classCallCheck(this, Markerable);\n\n _get(Object.getPrototypeOf(Markerable.prototype), 'constructor', this).call(this, type);\n this.isMarkerable = true;\n this.tagName = tagName;\n this.markers = new _mobiledocKitUtilsLinkedList['default']({\n adoptItem: function adoptItem(m) {\n (0, _mobiledocKitUtilsAssert['default'])('Can only insert markers and atoms into markerable (was: ' + m.type + ')', m.isMarker || m.isAtom);\n m.section = m.parent = _this;\n },\n freeItem: function freeItem(m) {\n return m.section = m.parent = null;\n }\n });\n\n markers.forEach(function (m) {\n return _this.markers.append(m);\n });\n }\n\n _createClass(Markerable, [{\n key: 'canJoin',\n value: function canJoin(other) {\n return other.isMarkerable && other.type === this.type && other.tagName === this.tagName;\n }\n }, {\n key: 'clone',\n value: function clone() {\n var newMarkers = this.markers.map(function (m) {\n return m.clone();\n });\n return this.builder.createMarkerableSection(this.type, this.tagName, newMarkers);\n }\n }, {\n key: 'textUntil',\n value: function textUntil(position) {\n (0, _mobiledocKitUtilsAssert['default'])('Cannot get textUntil for a position not in this section', position.section === this);\n var marker = position.marker;\n var offsetInMarker = position.offsetInMarker;\n\n var text = '';\n var currentMarker = this.markers.head;\n while (currentMarker) {\n if (currentMarker === marker) {\n text += currentMarker.textUntil(offsetInMarker);\n break;\n } else {\n text += currentMarker.text;\n currentMarker = currentMarker.next;\n }\n }\n return text;\n }\n\n /**\n * @param {Marker}\n * @param {Number} markerOffset The offset relative to the start of the marker\n *\n * @return {Number} The offset relative to the start of this section\n */\n }, {\n key: 'offsetOfMarker',\n value: function offsetOfMarker(marker) {\n var markerOffset = arguments.length <= 1 || arguments[1] === undefined ? 0 : arguments[1];\n\n (0, _mobiledocKitUtilsAssert['default'])('Cannot get offsetOfMarker for marker that is not child of this', marker.section === this);\n\n // FIXME it is possible, when we get a cursor position before having finished reparsing,\n // for markerOffset to be > marker.length. We shouldn't rely on this functionality.\n\n var offset = 0;\n var currentMarker = this.markers.head;\n while (currentMarker && currentMarker !== marker.next) {\n var _length = currentMarker === marker ? markerOffset : currentMarker.length;\n offset += _length;\n currentMarker = currentMarker.next;\n }\n\n return offset;\n }\n\n // puts clones of this.markers into beforeSection and afterSection,\n // all markers before the marker/offset split go in beforeSection, and all\n // after the marker/offset split go in afterSection\n // @return {Array} [beforeSection, afterSection], two new sections\n }, {\n key: '_redistributeMarkers',\n value: function _redistributeMarkers(beforeSection, afterSection, marker) {\n var offset = arguments.length <= 3 || arguments[3] === undefined ? 0 : arguments[3];\n\n var currentSection = beforeSection;\n (0, _mobiledocKitUtilsArrayUtils.forEach)(this.markers, function (m) {\n if (m === marker) {\n var _marker$split = marker.split(offset);\n\n var _marker$split2 = _toArray(_marker$split);\n\n var beforeMarker = _marker$split2[0];\n\n var afterMarkers = _marker$split2.slice(1);\n\n beforeSection.markers.append(beforeMarker);\n (0, _mobiledocKitUtilsArrayUtils.forEach)(afterMarkers, function (_m) {\n return afterSection.markers.append(_m);\n });\n currentSection = afterSection;\n } else {\n currentSection.markers.append(m.clone());\n }\n });\n\n return [beforeSection, afterSection];\n }\n }, {\n key: 'splitAtMarker',\n value: function splitAtMarker() /*marker, offset=0*/{\n (0, _mobiledocKitUtilsAssert['default'])('splitAtMarker must be implemented by sub-class', false);\n }\n\n /**\n * Split this section's marker (if any) at the given offset, so that\n * there is now a marker boundary at that offset (useful for later applying\n * a markup to a range)\n * @param {Number} sectionOffset The offset relative to start of this section\n * @return {EditObject} An edit object with 'removed' and 'added' keys with arrays of Markers. The added markers may be blank.\n * After calling `splitMarkerAtOffset(offset)`, there will always be a valid\n * result returned from `markerBeforeOffset(offset)`.\n */\n }, {\n key: 'splitMarkerAtOffset',\n value: function splitMarkerAtOffset(sectionOffset) {\n (0, _mobiledocKitUtilsAssert['default'])('Cannot splitMarkerAtOffset when offset is > length', sectionOffset <= this.length);\n var markerOffset = undefined;\n var len = 0;\n var currentMarker = this.markers.head;\n var edit = { added: [], removed: [] };\n\n if (!currentMarker) {\n var blankMarker = this.builder.createMarker();\n this.markers.prepend(blankMarker);\n edit.added.push(blankMarker);\n } else {\n while (currentMarker) {\n len += currentMarker.length;\n if (len === sectionOffset) {\n // nothing to do, there is a gap at the requested offset\n break;\n } else if (len > sectionOffset) {\n var _edit$added;\n\n markerOffset = currentMarker.length - (len - sectionOffset);\n var newMarkers = currentMarker.splitAtOffset(markerOffset);\n (_edit$added = edit.added).push.apply(_edit$added, _toConsumableArray(newMarkers));\n edit.removed.push(currentMarker);\n this.markers.splice(currentMarker, 1, newMarkers);\n break;\n } else {\n currentMarker = currentMarker.next;\n }\n }\n }\n\n return edit;\n }\n }, {\n key: 'splitAtPosition',\n value: function splitAtPosition(position) {\n var marker = position.marker;\n var offsetInMarker = position.offsetInMarker;\n\n return this.splitAtMarker(marker, offsetInMarker);\n }\n\n // returns the marker just before this offset.\n // It is an error to call this method with an offset that is in the middle\n // of a marker.\n }, {\n key: 'markerBeforeOffset',\n value: function markerBeforeOffset(sectionOffset) {\n var len = 0;\n var currentMarker = this.markers.head;\n\n while (currentMarker) {\n len += currentMarker.length;\n if (len === sectionOffset) {\n return currentMarker;\n } else {\n (0, _mobiledocKitUtilsAssert['default'])('markerBeforeOffset called with sectionOffset not between markers', len < sectionOffset);\n currentMarker = currentMarker.next;\n }\n }\n }\n }, {\n key: 'markerPositionAtOffset',\n value: function markerPositionAtOffset(offset) {\n var currentOffset = 0;\n var currentMarker = undefined;\n var remaining = offset;\n this.markers.detect(function (marker) {\n currentOffset = Math.min(remaining, marker.length);\n remaining -= currentOffset;\n if (remaining === 0) {\n currentMarker = marker;\n return true; // break out of detect\n }\n });\n\n return { marker: currentMarker, offset: currentOffset };\n }\n }, {\n key: 'markersFor',\n\n /**\n * @return {Array} New markers that match the boundaries of the\n * range. Does not change the existing markers in this section.\n */\n value: function markersFor(headOffset, tailOffset) {\n var range = { head: { section: this, offset: headOffset },\n tail: { section: this, offset: tailOffset } };\n\n var markers = [];\n this._markersInRange(range, function (marker, _ref) {\n var markerHead = _ref.markerHead;\n var markerTail = _ref.markerTail;\n var isContained = _ref.isContained;\n\n var cloned = marker.clone();\n if (!isContained) {\n // cannot do marker.value.slice if the marker is an atom -- this breaks the atom's \"atomic\" value\n // If a marker is an atom `isContained` should always be true so\n // we shouldn't hit this code path. FIXME add tests\n cloned.value = marker.value.slice(markerHead, markerTail);\n }\n markers.push(cloned);\n });\n return markers;\n }\n }, {\n key: 'markupsInRange',\n value: function markupsInRange(range) {\n var markups = new _mobiledocKitUtilsSet['default']();\n this._markersInRange(range, function (marker) {\n marker.markups.forEach(function (m) {\n return markups.add(m);\n });\n });\n return markups.toArray();\n }\n\n // calls the callback with (marker, {markerHead, markerTail, isContained})\n // for each marker that is wholly or partially contained in the range.\n }, {\n key: '_markersInRange',\n value: function _markersInRange(range, callback) {\n var head = range.head;\n var tail = range.tail;\n\n (0, _mobiledocKitUtilsAssert['default'])('Cannot call #_markersInRange if range expands beyond this section', head.section === this && tail.section === this);\n var headOffset = head.offset;var tailOffset = tail.offset;\n\n var currentHead = 0,\n currentTail = 0,\n currentMarker = this.markers.head;\n\n while (currentMarker) {\n currentTail += currentMarker.length;\n\n if (currentTail > headOffset && currentHead < tailOffset) {\n var markerHead = Math.max(headOffset - currentHead, 0);\n var markerTail = currentMarker.length - Math.max(currentTail - tailOffset, 0);\n var isContained = markerHead === 0 && markerTail === currentMarker.length;\n\n callback(currentMarker, { markerHead: markerHead, markerTail: markerTail, isContained: isContained });\n }\n\n currentHead += currentMarker.length;\n currentMarker = currentMarker.next;\n\n if (currentHead > tailOffset) {\n break;\n }\n }\n }\n\n // mutates this by appending the other section's (cloned) markers to it\n }, {\n key: 'join',\n value: function join(otherSection) {\n var _this2 = this;\n\n var beforeMarker = this.markers.tail;\n var afterMarker = null;\n\n otherSection.markers.forEach(function (m) {\n if (!m.isBlank) {\n m = m.clone();\n _this2.markers.append(m);\n if (!afterMarker) {\n afterMarker = m;\n }\n }\n });\n\n return { beforeMarker: beforeMarker, afterMarker: afterMarker };\n }\n }, {\n key: 'isBlank',\n get: function get() {\n if (!this.markers.length) {\n return true;\n }\n return this.markers.every(function (m) {\n return m.isBlank;\n });\n }\n }, {\n key: 'text',\n get: function get() {\n return (0, _mobiledocKitUtilsArrayUtils.reduce)(this.markers, function (prev, m) {\n return prev + m.value;\n }, '');\n }\n }, {\n key: 'length',\n get: function get() {\n return (0, _mobiledocKitUtilsArrayUtils.reduce)(this.markers, function (prev, m) {\n return prev + m.length;\n }, 0);\n }\n }]);\n\n return Markerable;\n })(_mobiledocKitModels_section['default']);\n\n exports['default'] = Markerable;\n});","define('mobiledoc-kit/models/_section', ['exports', 'mobiledoc-kit/utils/dom-utils', 'mobiledoc-kit/utils/linked-item', 'mobiledoc-kit/utils/assert', 'mobiledoc-kit/utils/cursor/position'], function (exports, _mobiledocKitUtilsDomUtils, _mobiledocKitUtilsLinkedItem, _mobiledocKitUtilsAssert, _mobiledocKitUtilsCursorPosition) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n var _get = function get(_x, _x2, _x3) { var _again = true; _function: while (_again) { var object = _x, property = _x2, receiver = _x3; _again = false; if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { _x = parent; _x2 = property; _x3 = receiver; _again = true; desc = parent = undefined; continue _function; } } else if ('value' in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } } };\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n function _inherits(subClass, superClass) { if (typeof superClass !== 'function' && superClass !== null) { throw new TypeError('Super expression must either be null or a function, not ' + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }\n\n function unimplementedMethod(methodName, me) {\n (0, _mobiledocKitUtilsAssert['default'])('`' + methodName + '()` must be implemented by ' + me.constructor.name, false);\n }\n\n var Section = (function (_LinkedItem) {\n _inherits(Section, _LinkedItem);\n\n function Section(type) {\n _classCallCheck(this, Section);\n\n _get(Object.getPrototypeOf(Section.prototype), 'constructor', this).call(this);\n (0, _mobiledocKitUtilsAssert['default'])('Cannot create section without type', !!type);\n this.type = type;\n this.isSection = true;\n this.isMarkerable = false;\n this.isNested = false;\n this.isSection = true;\n this.isLeafSection = true;\n }\n\n _createClass(Section, [{\n key: 'isValidTagName',\n value: function isValidTagName() /* normalizedTagName */{\n unimplementedMethod('isValidTagName', this);\n }\n }, {\n key: 'clone',\n value: function clone() {\n unimplementedMethod('clone', this);\n }\n }, {\n key: 'canJoin',\n value: function canJoin() /* otherSection */{\n unimplementedMethod('canJoin', this);\n }\n\n /**\n * @return {Position} The position at the start of this section\n * @public\n */\n }, {\n key: 'headPosition',\n value: function headPosition() {\n return this.toPosition(0);\n }\n\n /**\n * @return {Position} The position at the end of this section\n * @public\n */\n }, {\n key: 'tailPosition',\n value: function tailPosition() {\n return this.toPosition(this.length);\n }\n\n /**\n * @param {Number} offset\n * @return {Position} The position in this section at the given offset\n * @public\n */\n }, {\n key: 'toPosition',\n value: function toPosition(offset) {\n (0, _mobiledocKitUtilsAssert['default'])(\"Must pass number to `toPosition`\", typeof offset === 'number');\n (0, _mobiledocKitUtilsAssert['default'])(\"Cannot call `toPosition` with offset > length\", offset <= this.length);\n\n return new _mobiledocKitUtilsCursorPosition['default'](this, offset);\n }\n\n /**\n * @return {Range} A range from this section's head to tail positions\n * @public\n */\n }, {\n key: 'toRange',\n value: function toRange() {\n return this.headPosition().toRange(this.tailPosition());\n }\n }, {\n key: 'join',\n value: function join() {\n unimplementedMethod('join', this);\n }\n }, {\n key: 'textUntil',\n value: function textUntil() /* position */{\n return '';\n }\n\n /**\n * Markerable sections should override this method\n */\n }, {\n key: 'splitMarkerAtOffset',\n value: function splitMarkerAtOffset() {\n var blankEdit = { added: [], removed: [] };\n return blankEdit;\n }\n }, {\n key: 'nextLeafSection',\n value: function nextLeafSection() {\n var next = this.next;\n if (next) {\n if (!!next.items) {\n return next.items.head;\n } else {\n return next;\n }\n } else {\n if (this.isNested) {\n return this.parent.nextLeafSection();\n }\n }\n }\n }, {\n key: 'immediatelyNextMarkerableSection',\n value: function immediatelyNextMarkerableSection() {\n var next = this.nextLeafSection();\n while (next && !next.isMarkerable) {\n next = next.nextLeafSection();\n }\n return next;\n }\n }, {\n key: 'previousLeafSection',\n value: function previousLeafSection() {\n var prev = this.prev;\n\n if (prev) {\n if (!!prev.items) {\n return prev.items.tail;\n } else {\n return prev;\n }\n } else {\n if (this.isNested) {\n return this.parent.previousLeafSection();\n }\n }\n }\n }, {\n key: 'tagName',\n set: function set(val) {\n var normalizedTagName = (0, _mobiledocKitUtilsDomUtils.normalizeTagName)(val);\n (0, _mobiledocKitUtilsAssert['default'])('Cannot set section tagName to ' + val, this.isValidTagName(normalizedTagName));\n this._tagName = normalizedTagName;\n },\n get: function get() {\n return this._tagName;\n }\n }, {\n key: 'length',\n get: function get() {\n return 0;\n }\n }, {\n key: 'isBlank',\n get: function get() {\n unimplementedMethod('isBlank', this);\n }\n }]);\n\n return Section;\n })(_mobiledocKitUtilsLinkedItem['default']);\n\n exports['default'] = Section;\n});","define('mobiledoc-kit/models/atom-node', ['exports', 'mobiledoc-kit/utils/assert'], function (exports, _mobiledocKitUtilsAssert) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n var AtomNode = (function () {\n function AtomNode(editor, atom, model, element, atomOptions) {\n _classCallCheck(this, AtomNode);\n\n this.editor = editor;\n this.atom = atom;\n this.model = model;\n this.atomOptions = atomOptions;\n this.element = element;\n\n this._teardownCallback = null;\n this._rendered = null;\n }\n\n _createClass(AtomNode, [{\n key: 'render',\n value: function render() {\n if (!this._rendered) {\n var options = this.atomOptions;\n var env = this.env;\n var _model = this.model;\n var value = _model.value;\n var payload = _model.payload;\n\n // cache initial render\n this._rendered = this.atom.render({ options: options, env: env, value: value, payload: payload });\n }\n\n this._validateAndAppendRenderResult(this._rendered);\n }\n }, {\n key: 'teardown',\n value: function teardown() {\n if (this._teardownCallback) {\n this._teardownCallback();\n this._teardownCallback = null;\n }\n if (this._rendered) {\n this.element.removeChild(this._rendered);\n this._rendered = null;\n }\n }\n }, {\n key: '_validateAndAppendRenderResult',\n value: function _validateAndAppendRenderResult(rendered) {\n if (!rendered) {\n return;\n }\n\n var name = this.atom.name;\n\n (0, _mobiledocKitUtilsAssert['default'])('Atom \"' + name + '\" must return a DOM node (returned value was: \"' + rendered + '\")', !!rendered.nodeType);\n this.element.appendChild(rendered);\n }\n }, {\n key: 'env',\n get: function get() {\n var _this = this;\n\n return {\n name: this.atom.name,\n onTeardown: function onTeardown(callback) {\n return _this._teardownCallback = callback;\n },\n save: function save(value) {\n var payload = arguments.length <= 1 || arguments[1] === undefined ? {} : arguments[1];\n\n _this.model.value = value;\n _this.model.payload = payload;\n\n _this.editor._postDidChange();\n _this.teardown();\n _this.render();\n }\n };\n }\n }]);\n\n return AtomNode;\n })();\n\n exports['default'] = AtomNode;\n});","define('mobiledoc-kit/models/atom', ['exports', 'mobiledoc-kit/models/types', 'mobiledoc-kit/utils/mixin', 'mobiledoc-kit/utils/markuperable', 'mobiledoc-kit/utils/linked-item', 'mobiledoc-kit/utils/assert'], function (exports, _mobiledocKitModelsTypes, _mobiledocKitUtilsMixin, _mobiledocKitUtilsMarkuperable, _mobiledocKitUtilsLinkedItem, _mobiledocKitUtilsAssert) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n var _get = function get(_x4, _x5, _x6) { var _again = true; _function: while (_again) { var object = _x4, property = _x5, receiver = _x6; _again = false; if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { _x4 = parent; _x5 = property; _x6 = receiver; _again = true; desc = parent = undefined; continue _function; } } else if ('value' in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } } };\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n function _inherits(subClass, superClass) { if (typeof superClass !== 'function' && superClass !== null) { throw new TypeError('Super expression must either be null or a function, not ' + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }\n\n var ATOM_LENGTH = 1;\n\n var Atom = (function (_LinkedItem) {\n _inherits(Atom, _LinkedItem);\n\n function Atom(name, value, payload) {\n var _this = this;\n\n var markups = arguments.length <= 3 || arguments[3] === undefined ? [] : arguments[3];\n\n _classCallCheck(this, Atom);\n\n _get(Object.getPrototypeOf(Atom.prototype), 'constructor', this).call(this);\n this.name = name;\n this.value = value;\n this.text = ''; // An atom never has text, but it does have a value\n (0, _mobiledocKitUtilsAssert['default'])('Atom must have value', value !== undefined && value !== null);\n this.payload = payload;\n this.type = _mobiledocKitModelsTypes.ATOM_TYPE;\n this.isMarker = false;\n this.isAtom = true;\n\n this.markups = [];\n markups.forEach(function (m) {\n return _this.addMarkup(m);\n });\n }\n\n _createClass(Atom, [{\n key: 'clone',\n value: function clone() {\n var clonedMarkups = this.markups.slice();\n return this.builder.createAtom(this.name, this.value, this.payload, clonedMarkups);\n }\n }, {\n key: 'canJoin',\n value: function canJoin() /* other */{\n return false;\n }\n }, {\n key: 'textUntil',\n value: function textUntil() /* offset */{\n return '';\n }\n }, {\n key: 'split',\n value: function split() {\n var offset = arguments.length <= 0 || arguments[0] === undefined ? 0 : arguments[0];\n var endOffset = arguments.length <= 1 || arguments[1] === undefined ? offset : arguments[1];\n return (function () {\n var markers = [];\n\n if (endOffset === 0) {\n markers.push(this.builder.createMarker('', this.markups.slice()));\n }\n\n markers.push(this.clone());\n\n if (offset === ATOM_LENGTH) {\n markers.push(this.builder.createMarker('', this.markups.slice()));\n }\n\n return markers;\n }).apply(this, arguments);\n }\n }, {\n key: 'splitAtOffset',\n value: function splitAtOffset(offset) {\n (0, _mobiledocKitUtilsAssert['default'])('Cannot split a marker at an offset > its length', offset <= this.length);\n\n var builder = this.builder;\n\n var clone = this.clone();\n var blankMarker = builder.createMarker('');\n var pre = undefined,\n post = undefined;\n\n if (offset === 0) {\n pre = blankMarker;\n post = clone;\n } else if (offset === ATOM_LENGTH) {\n pre = clone;\n post = blankMarker;\n } else {\n (0, _mobiledocKitUtilsAssert['default'])('Invalid offset given to Atom#splitAtOffset: \"' + offset + '\"', false);\n }\n\n this.markups.forEach(function (markup) {\n pre.addMarkup(markup);\n post.addMarkup(markup);\n });\n return [pre, post];\n }\n }, {\n key: 'isBlank',\n get: function get() {\n return false;\n }\n }, {\n key: 'length',\n get: function get() {\n return ATOM_LENGTH;\n }\n }]);\n\n return Atom;\n })(_mobiledocKitUtilsLinkedItem['default']);\n\n (0, _mobiledocKitUtilsMixin['default'])(Atom, _mobiledocKitUtilsMarkuperable['default']);\n\n exports['default'] = Atom;\n});","define('mobiledoc-kit/models/card-node', ['exports', 'mobiledoc-kit/utils/assert'], function (exports, _mobiledocKitUtilsAssert) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n var CardNode = (function () {\n function CardNode(editor, card, section, element, options) {\n _classCallCheck(this, CardNode);\n\n this.editor = editor;\n this.card = card;\n this.section = section;\n this.element = element;\n this.options = options;\n\n this.mode = null;\n\n this._teardownCallback = null;\n this._rendered = null;\n }\n\n _createClass(CardNode, [{\n key: 'render',\n value: function render(mode) {\n if (this.mode === mode) {\n return;\n }\n\n this.teardown();\n\n this.mode = mode;\n\n var method = mode === 'display' ? 'render' : 'edit';\n method = this.card[method];\n\n (0, _mobiledocKitUtilsAssert['default'])('Card is missing \"' + method + '\" (tried to render mode: \"' + mode + '\")', !!method);\n var rendered = method({\n env: this.env,\n options: this.options,\n payload: this.section.payload\n });\n\n this._validateAndAppendRenderResult(rendered);\n }\n }, {\n key: 'teardown',\n value: function teardown() {\n if (this._teardownCallback) {\n this._teardownCallback();\n this._teardownCallback = null;\n }\n if (this._rendered) {\n this.element.removeChild(this._rendered);\n this._rendered = null;\n }\n }\n }, {\n key: 'didRender',\n value: function didRender() {\n if (this._didRenderCallback) {\n this._didRenderCallback();\n }\n }\n }, {\n key: 'display',\n value: function display() {\n this.render('display');\n }\n }, {\n key: 'edit',\n value: function edit() {\n this.render('edit');\n }\n }, {\n key: 'remove',\n value: function remove() {\n var _this = this;\n\n this.editor.run(function (postEditor) {\n return postEditor.removeSection(_this.section);\n });\n }\n }, {\n key: '_validateAndAppendRenderResult',\n value: function _validateAndAppendRenderResult(rendered) {\n if (!rendered) {\n return;\n }\n\n var name = this.card.name;\n\n (0, _mobiledocKitUtilsAssert['default'])('Card \"' + name + '\" must render dom (render value was: \"' + rendered + '\")', !!rendered.nodeType);\n this.element.appendChild(rendered);\n this._rendered = rendered;\n this.didRender();\n }\n }, {\n key: 'env',\n get: function get() {\n var _this2 = this;\n\n return {\n name: this.card.name,\n isInEditor: true,\n onTeardown: function onTeardown(callback) {\n return _this2._teardownCallback = callback;\n },\n didRender: function didRender(callback) {\n return _this2._didRenderCallback = callback;\n },\n edit: function edit() {\n return _this2.edit();\n },\n save: function save(payload) {\n var transition = arguments.length <= 1 || arguments[1] === undefined ? true : arguments[1];\n\n _this2.section.payload = payload;\n\n _this2.editor._postDidChange();\n if (transition) {\n _this2.display();\n }\n },\n cancel: function cancel() {\n return _this2.display();\n },\n remove: function remove() {\n return _this2.remove();\n },\n postModel: this.section\n };\n }\n }]);\n\n return CardNode;\n })();\n\n exports['default'] = CardNode;\n});","define('mobiledoc-kit/models/card', ['exports', 'mobiledoc-kit/models/_section', 'mobiledoc-kit/models/types', 'mobiledoc-kit/utils/copy'], function (exports, _mobiledocKitModels_section, _mobiledocKitModelsTypes, _mobiledocKitUtilsCopy) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n var _get = function get(_x, _x2, _x3) { var _again = true; _function: while (_again) { var object = _x, property = _x2, receiver = _x3; _again = false; if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { _x = parent; _x2 = property; _x3 = receiver; _again = true; desc = parent = undefined; continue _function; } } else if ('value' in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } } };\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n function _inherits(subClass, superClass) { if (typeof superClass !== 'function' && superClass !== null) { throw new TypeError('Super expression must either be null or a function, not ' + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }\n\n var CARD_MODES = {\n DISPLAY: 'display',\n EDIT: 'edit'\n };\n\n exports.CARD_MODES = CARD_MODES;\n var CARD_LENGTH = 1;\n\n var DEFAULT_INITIAL_MODE = CARD_MODES.DISPLAY;\n\n var Card = (function (_Section) {\n _inherits(Card, _Section);\n\n function Card(name, payload) {\n _classCallCheck(this, Card);\n\n _get(Object.getPrototypeOf(Card.prototype), 'constructor', this).call(this, _mobiledocKitModelsTypes.CARD_TYPE);\n this.name = name;\n this.payload = payload;\n this.setInitialMode(DEFAULT_INITIAL_MODE);\n this.isCardSection = true;\n }\n\n _createClass(Card, [{\n key: 'canJoin',\n value: function canJoin() {\n return false;\n }\n }, {\n key: 'clone',\n value: function clone() {\n var payload = (0, _mobiledocKitUtilsCopy.shallowCopyObject)(this.payload);\n var card = this.builder.createCardSection(this.name, payload);\n // If this card is currently rendered, clone the mode it is\n // currently in as the default mode of the new card.\n var mode = this._initialMode;\n if (this.renderNode && this.renderNode.cardNode) {\n mode = this.renderNode.cardNode.mode;\n }\n card.setInitialMode(mode);\n return card;\n }\n\n /**\n * set the mode that this will be rendered into initially\n * @private\n */\n }, {\n key: 'setInitialMode',\n value: function setInitialMode(initialMode) {\n // TODO validate initialMode\n this._initialMode = initialMode;\n }\n }, {\n key: 'isBlank',\n get: function get() {\n return false;\n }\n }, {\n key: 'length',\n get: function get() {\n return CARD_LENGTH;\n }\n }]);\n\n return Card;\n })(_mobiledocKitModels_section['default']);\n\n exports['default'] = Card;\n});","define('mobiledoc-kit/models/image', ['exports', 'mobiledoc-kit/models/types', 'mobiledoc-kit/models/_section'], function (exports, _mobiledocKitModelsTypes, _mobiledocKitModels_section) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n var _get = function get(_x, _x2, _x3) { var _again = true; _function: while (_again) { var object = _x, property = _x2, receiver = _x3; _again = false; if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { _x = parent; _x2 = property; _x3 = receiver; _again = true; desc = parent = undefined; continue _function; } } else if ('value' in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } } };\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n function _inherits(subClass, superClass) { if (typeof superClass !== 'function' && superClass !== null) { throw new TypeError('Super expression must either be null or a function, not ' + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }\n\n var Image = (function (_Section) {\n _inherits(Image, _Section);\n\n function Image() {\n _classCallCheck(this, Image);\n\n _get(Object.getPrototypeOf(Image.prototype), 'constructor', this).call(this, _mobiledocKitModelsTypes.IMAGE_SECTION_TYPE);\n this.src = null;\n }\n\n _createClass(Image, [{\n key: 'canJoin',\n value: function canJoin() {\n return false;\n }\n }, {\n key: 'isBlank',\n get: function get() {\n return false;\n }\n }, {\n key: 'length',\n get: function get() {\n return 1;\n }\n }]);\n\n return Image;\n })(_mobiledocKitModels_section['default']);\n\n exports['default'] = Image;\n});","define('mobiledoc-kit/models/lifecycle-callbacks', ['exports', 'mobiledoc-kit/utils/assert'], function (exports, _mobiledocKitUtilsAssert) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _toConsumableArray(arr) { if (Array.isArray(arr)) { for (var i = 0, arr2 = Array(arr.length); i < arr.length; i++) arr2[i] = arr[i]; return arr2; } else { return Array.from(arr); } }\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n var LifecycleCallbacks = (function () {\n function LifecycleCallbacks() {\n var _this = this;\n\n var queueNames = arguments.length <= 0 || arguments[0] === undefined ? [] : arguments[0];\n\n _classCallCheck(this, LifecycleCallbacks);\n\n this.callbackQueues = {};\n this.removalQueues = {};\n\n queueNames.forEach(function (name) {\n _this.callbackQueues[name] = [];\n _this.removalQueues[name] = [];\n });\n }\n\n _createClass(LifecycleCallbacks, [{\n key: 'runCallbacks',\n value: function runCallbacks(queueName) {\n var args = arguments.length <= 1 || arguments[1] === undefined ? [] : arguments[1];\n\n var queue = this._getQueue(queueName);\n queue.forEach(function (cb) {\n return cb.apply(undefined, _toConsumableArray(args));\n });\n\n var toRemove = this.removalQueues[queueName];\n toRemove.forEach(function (cb) {\n var index = queue.indexOf(cb);\n if (index !== -1) {\n queue.splice(index, 1);\n }\n });\n\n this.removalQueues[queueName] = [];\n }\n }, {\n key: 'addCallback',\n value: function addCallback(queueName, callback) {\n this._getQueue(queueName).push(callback);\n }\n }, {\n key: '_scheduleCallbackForRemoval',\n value: function _scheduleCallbackForRemoval(queueName, callback) {\n this.removalQueues[queueName].push(callback);\n }\n }, {\n key: 'addCallbackOnce',\n value: function addCallbackOnce(queueName, callback) {\n var queue = this._getQueue(queueName);\n if (queue.indexOf(callback) === -1) {\n queue.push(callback);\n this._scheduleCallbackForRemoval(queueName, callback);\n }\n }\n }, {\n key: '_getQueue',\n value: function _getQueue(queueName) {\n var queue = this.callbackQueues[queueName];\n (0, _mobiledocKitUtilsAssert['default'])('No queue found for \"' + queueName + '\"', !!queue);\n return queue;\n }\n }]);\n\n return LifecycleCallbacks;\n })();\n\n exports['default'] = LifecycleCallbacks;\n});","define('mobiledoc-kit/models/list-item', ['exports', 'mobiledoc-kit/models/_markerable', 'mobiledoc-kit/models/types', 'mobiledoc-kit/utils/dom-utils', 'mobiledoc-kit/utils/array-utils'], function (exports, _mobiledocKitModels_markerable, _mobiledocKitModelsTypes, _mobiledocKitUtilsDomUtils, _mobiledocKitUtilsArrayUtils) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n var _get = function get(_x3, _x4, _x5) { var _again = true; _function: while (_again) { var object = _x3, property = _x4, receiver = _x5; _again = false; if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { _x3 = parent; _x4 = property; _x5 = receiver; _again = true; desc = parent = undefined; continue _function; } } else if ('value' in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } } };\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n function _inherits(subClass, superClass) { if (typeof superClass !== 'function' && superClass !== null) { throw new TypeError('Super expression must either be null or a function, not ' + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }\n\n var VALID_LIST_ITEM_TAGNAMES = ['li'].map(_mobiledocKitUtilsDomUtils.normalizeTagName);\n\n exports.VALID_LIST_ITEM_TAGNAMES = VALID_LIST_ITEM_TAGNAMES;\n\n var ListItem = (function (_Markerable) {\n _inherits(ListItem, _Markerable);\n\n function ListItem(tagName) {\n var markers = arguments.length <= 1 || arguments[1] === undefined ? [] : arguments[1];\n\n _classCallCheck(this, ListItem);\n\n _get(Object.getPrototypeOf(ListItem.prototype), 'constructor', this).call(this, _mobiledocKitModelsTypes.LIST_ITEM_TYPE, tagName, markers);\n this.isListItem = true;\n this.isNested = true;\n }\n\n _createClass(ListItem, [{\n key: 'isValidTagName',\n value: function isValidTagName(normalizedTagName) {\n return (0, _mobiledocKitUtilsArrayUtils.contains)(VALID_LIST_ITEM_TAGNAMES, normalizedTagName);\n }\n }, {\n key: 'splitAtMarker',\n value: function splitAtMarker(marker) {\n var offset = arguments.length <= 1 || arguments[1] === undefined ? 0 : arguments[1];\n\n // FIXME need to check if we are going to split into two list items\n // or a list item and a new markup section:\n var isLastItem = !this.next;\n var createNewSection = !marker && offset === 0 && isLastItem;\n\n var beforeSection = this.builder.createListItem();\n var afterSection = createNewSection ? this.builder.createMarkupSection() : this.builder.createListItem();\n\n return this._redistributeMarkers(beforeSection, afterSection, marker, offset);\n }\n }, {\n key: 'post',\n get: function get() {\n return this.section.post;\n }\n }]);\n\n return ListItem;\n })(_mobiledocKitModels_markerable['default']);\n\n exports['default'] = ListItem;\n});","define('mobiledoc-kit/models/list-section', ['exports', 'mobiledoc-kit/utils/linked-list', 'mobiledoc-kit/utils/array-utils', 'mobiledoc-kit/models/types', 'mobiledoc-kit/models/_section', 'mobiledoc-kit/utils/dom-utils', 'mobiledoc-kit/utils/assert'], function (exports, _mobiledocKitUtilsLinkedList, _mobiledocKitUtilsArrayUtils, _mobiledocKitModelsTypes, _mobiledocKitModels_section, _mobiledocKitUtilsDomUtils, _mobiledocKitUtilsAssert) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n var _get = function get(_x3, _x4, _x5) { var _again = true; _function: while (_again) { var object = _x3, property = _x4, receiver = _x5; _again = false; if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { _x3 = parent; _x4 = property; _x5 = receiver; _again = true; desc = parent = undefined; continue _function; } } else if ('value' in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } } };\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n function _inherits(subClass, superClass) { if (typeof superClass !== 'function' && superClass !== null) { throw new TypeError('Super expression must either be null or a function, not ' + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }\n\n var VALID_LIST_SECTION_TAGNAMES = ['ul', 'ol'].map(_mobiledocKitUtilsDomUtils.normalizeTagName);\n\n exports.VALID_LIST_SECTION_TAGNAMES = VALID_LIST_SECTION_TAGNAMES;\n var DEFAULT_TAG_NAME = VALID_LIST_SECTION_TAGNAMES[0];\n\n exports.DEFAULT_TAG_NAME = DEFAULT_TAG_NAME;\n\n var ListSection = (function (_Section) {\n _inherits(ListSection, _Section);\n\n function ListSection() {\n var _this = this;\n\n var tagName = arguments.length <= 0 || arguments[0] === undefined ? DEFAULT_TAG_NAME : arguments[0];\n var items = arguments.length <= 1 || arguments[1] === undefined ? [] : arguments[1];\n\n _classCallCheck(this, ListSection);\n\n _get(Object.getPrototypeOf(ListSection.prototype), 'constructor', this).call(this, _mobiledocKitModelsTypes.LIST_SECTION_TYPE);\n this.tagName = tagName;\n this.isListSection = true;\n this.isLeafSection = false;\n\n this.items = new _mobiledocKitUtilsLinkedList['default']({\n adoptItem: function adoptItem(i) {\n (0, _mobiledocKitUtilsAssert['default'])('Cannot insert non-list-item to list (is: ' + i.type + ')', i.isListItem);\n i.section = i.parent = _this;\n },\n freeItem: function freeItem(i) {\n return i.section = i.parent = null;\n }\n });\n this.sections = this.items;\n\n items.forEach(function (i) {\n return _this.items.append(i);\n });\n }\n\n _createClass(ListSection, [{\n key: 'canJoin',\n value: function canJoin() {\n return false;\n }\n }, {\n key: 'isValidTagName',\n value: function isValidTagName(normalizedTagName) {\n return (0, _mobiledocKitUtilsArrayUtils.contains)(VALID_LIST_SECTION_TAGNAMES, normalizedTagName);\n }\n }, {\n key: 'headPosition',\n value: function headPosition() {\n return this.items.head.headPosition();\n }\n }, {\n key: 'tailPosition',\n value: function tailPosition() {\n return this.items.tail.tailPosition();\n }\n }, {\n key: 'clone',\n value: function clone() {\n var newSection = this.builder.createListSection(this.tagName);\n (0, _mobiledocKitUtilsArrayUtils.forEach)(this.items, function (i) {\n return newSection.items.append(i.clone());\n });\n return newSection;\n }\n\n /**\n * Mutates this list\n * @param {ListSection|Markerable}\n * @return null\n */\n }, {\n key: 'join',\n value: function join(other) {\n var _this2 = this;\n\n if (other.isListSection) {\n other.items.forEach(function (i) {\n return _this2.join(i);\n });\n } else if (other.isMarkerable) {\n var item = this.builder.createListItem();\n item.join(other);\n this.items.append(item);\n }\n }\n }, {\n key: 'isBlank',\n get: function get() {\n return this.items.isEmpty;\n }\n }]);\n\n return ListSection;\n })(_mobiledocKitModels_section['default']);\n\n exports['default'] = ListSection;\n});","define('mobiledoc-kit/models/marker', ['exports', 'mobiledoc-kit/models/types', 'mobiledoc-kit/utils/mixin', 'mobiledoc-kit/utils/markuperable', 'mobiledoc-kit/utils/linked-item', 'mobiledoc-kit/utils/assert', 'mobiledoc-kit/utils/array-utils'], function (exports, _mobiledocKitModelsTypes, _mobiledocKitUtilsMixin, _mobiledocKitUtilsMarkuperable, _mobiledocKitUtilsLinkedItem, _mobiledocKitUtilsAssert, _mobiledocKitUtilsArrayUtils) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n var _get = function get(_x5, _x6, _x7) { var _again = true; _function: while (_again) { var object = _x5, property = _x6, receiver = _x7; _again = false; if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { _x5 = parent; _x6 = property; _x7 = receiver; _again = true; desc = parent = undefined; continue _function; } } else if ('value' in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } } };\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n function _inherits(subClass, superClass) { if (typeof superClass !== 'function' && superClass !== null) { throw new TypeError('Super expression must either be null or a function, not ' + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }\n\n // Unicode uses a pair of \"surrogate\" characters\" (a high- and low-surrogate)\n // to encode characters outside the basic multilingual plane (like emoji and\n // some languages).\n // These values are the unicode code points for the start and end of the\n // high- and low-surrogate characters.\n // See \"high surrogate\" and \"low surrogate\" on\n // https://en.wikipedia.org/wiki/Unicode_block\n var HIGH_SURROGATE_RANGE = [0xD800, 0xDBFF];\n exports.HIGH_SURROGATE_RANGE = HIGH_SURROGATE_RANGE;\n var LOW_SURROGATE_RANGE = [0xDC00, 0xDFFF];\n\n exports.LOW_SURROGATE_RANGE = LOW_SURROGATE_RANGE;\n var Marker = (function (_LinkedItem) {\n _inherits(Marker, _LinkedItem);\n\n function Marker() {\n var _this = this;\n\n var value = arguments.length <= 0 || arguments[0] === undefined ? '' : arguments[0];\n var markups = arguments.length <= 1 || arguments[1] === undefined ? [] : arguments[1];\n\n _classCallCheck(this, Marker);\n\n _get(Object.getPrototypeOf(Marker.prototype), 'constructor', this).call(this);\n this.value = value;\n (0, _mobiledocKitUtilsAssert['default'])('Marker must have value', value !== undefined && value !== null);\n this.markups = [];\n this.type = _mobiledocKitModelsTypes.MARKER_TYPE;\n this.isMarker = true;\n this.isAtom = false;\n markups.forEach(function (m) {\n return _this.addMarkup(m);\n });\n }\n\n _createClass(Marker, [{\n key: 'clone',\n value: function clone() {\n var clonedMarkups = this.markups.slice();\n return this.builder.createMarker(this.value, clonedMarkups);\n }\n }, {\n key: 'charAt',\n value: function charAt(offset) {\n return this.value.slice(offset, offset + 1);\n }\n\n /**\n * A marker's text is equal to its value.\n * Compare with an Atom which distinguishes between text and value\n */\n }, {\n key: 'deleteValueAtOffset',\n\n // delete the character at this offset,\n // update the value with the new value\n value: function deleteValueAtOffset(offset) {\n (0, _mobiledocKitUtilsAssert['default'])('Cannot delete value at offset outside bounds', offset >= 0 && offset <= this.length);\n\n var width = 1;\n var code = this.value.charCodeAt(offset);\n if (code >= HIGH_SURROGATE_RANGE[0] && code <= HIGH_SURROGATE_RANGE[1]) {\n width = 2;\n } else if (code >= LOW_SURROGATE_RANGE[0] && code <= LOW_SURROGATE_RANGE[1]) {\n width = 2;\n offset = offset - 1;\n }\n\n var left = this.value.slice(0, offset);\n var right = this.value.slice(offset + width);\n\n this.value = left + right;\n\n return width;\n }\n }, {\n key: 'canJoin',\n value: function canJoin(other) {\n return other && other.isMarker && (0, _mobiledocKitUtilsArrayUtils.isArrayEqual)(this.markups, other.markups);\n }\n }, {\n key: 'textUntil',\n value: function textUntil(offset) {\n return this.value.slice(0, offset);\n }\n }, {\n key: 'split',\n value: function split() {\n var offset = arguments.length <= 0 || arguments[0] === undefined ? 0 : arguments[0];\n var endOffset = arguments.length <= 1 || arguments[1] === undefined ? this.length : arguments[1];\n\n var markers = [this.builder.createMarker(this.value.substring(0, offset)), this.builder.createMarker(this.value.substring(offset, endOffset)), this.builder.createMarker(this.value.substring(endOffset))];\n\n this.markups.forEach(function (mu) {\n return markers.forEach(function (m) {\n return m.addMarkup(mu);\n });\n });\n return markers;\n }\n\n /**\n * @return {Array} 2 markers either or both of which could be blank\n */\n }, {\n key: 'splitAtOffset',\n value: function splitAtOffset(offset) {\n (0, _mobiledocKitUtilsAssert['default'])('Cannot split a marker at an offset > its length', offset <= this.length);\n var value = this.value;\n var builder = this.builder;\n\n var pre = builder.createMarker(value.substring(0, offset));\n var post = builder.createMarker(value.substring(offset));\n\n this.markups.forEach(function (markup) {\n pre.addMarkup(markup);\n post.addMarkup(markup);\n });\n\n return [pre, post];\n }\n }, {\n key: 'isEmpty',\n get: function get() {\n return this.isBlank;\n }\n }, {\n key: 'isBlank',\n get: function get() {\n return this.length === 0;\n }\n }, {\n key: 'text',\n get: function get() {\n return this.value;\n }\n }, {\n key: 'length',\n get: function get() {\n return this.value.length;\n }\n }]);\n\n return Marker;\n })(_mobiledocKitUtilsLinkedItem['default']);\n\n (0, _mobiledocKitUtilsMixin['default'])(Marker, _mobiledocKitUtilsMarkuperable['default']);\n\n exports['default'] = Marker;\n});","define('mobiledoc-kit/models/markup-section', ['exports', 'mobiledoc-kit/models/_markerable', 'mobiledoc-kit/utils/dom-utils', 'mobiledoc-kit/utils/array-utils', 'mobiledoc-kit/models/types'], function (exports, _mobiledocKitModels_markerable, _mobiledocKitUtilsDomUtils, _mobiledocKitUtilsArrayUtils, _mobiledocKitModelsTypes) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n var _get = function get(_x4, _x5, _x6) { var _again = true; _function: while (_again) { var object = _x4, property = _x5, receiver = _x6; _again = false; if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { _x4 = parent; _x5 = property; _x6 = receiver; _again = true; desc = parent = undefined; continue _function; } } else if ('value' in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } } };\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n function _inherits(subClass, superClass) { if (typeof superClass !== 'function' && superClass !== null) { throw new TypeError('Super expression must either be null or a function, not ' + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }\n\n // valid values of `tagName` for a MarkupSection\n var VALID_MARKUP_SECTION_TAGNAMES = ['p', 'h3', 'h2', 'h1', 'blockquote', 'pull-quote'].map(_mobiledocKitUtilsDomUtils.normalizeTagName);\n\n exports.VALID_MARKUP_SECTION_TAGNAMES = VALID_MARKUP_SECTION_TAGNAMES;\n // valid element names for a MarkupSection. A MarkupSection with a tagName\n // not in this will be rendered as a div with a className matching the\n // tagName\n var MARKUP_SECTION_ELEMENT_NAMES = ['p', 'h3', 'h2', 'h1', 'blockquote'].map(_mobiledocKitUtilsDomUtils.normalizeTagName);\n exports.MARKUP_SECTION_ELEMENT_NAMES = MARKUP_SECTION_ELEMENT_NAMES;\n var DEFAULT_TAG_NAME = VALID_MARKUP_SECTION_TAGNAMES[0];\n\n exports.DEFAULT_TAG_NAME = DEFAULT_TAG_NAME;\n var MarkupSection = (function (_Markerable) {\n _inherits(MarkupSection, _Markerable);\n\n function MarkupSection() {\n var tagName = arguments.length <= 0 || arguments[0] === undefined ? DEFAULT_TAG_NAME : arguments[0];\n var markers = arguments.length <= 1 || arguments[1] === undefined ? [] : arguments[1];\n\n _classCallCheck(this, MarkupSection);\n\n _get(Object.getPrototypeOf(MarkupSection.prototype), 'constructor', this).call(this, _mobiledocKitModelsTypes.MARKUP_SECTION_TYPE, tagName, markers);\n this.isMarkupSection = true;\n }\n\n _createClass(MarkupSection, [{\n key: 'isValidTagName',\n value: function isValidTagName(normalizedTagName) {\n return (0, _mobiledocKitUtilsArrayUtils.contains)(VALID_MARKUP_SECTION_TAGNAMES, normalizedTagName);\n }\n }, {\n key: 'splitAtMarker',\n value: function splitAtMarker(marker) {\n var offset = arguments.length <= 1 || arguments[1] === undefined ? 0 : arguments[1];\n var beforeSection = this.builder.createMarkupSection(this.tagName, []);\n var afterSection = this.builder.createMarkupSection();\n\n return this._redistributeMarkers(beforeSection, afterSection, marker, offset);\n }\n }]);\n\n return MarkupSection;\n })(_mobiledocKitModels_markerable['default']);\n\n exports['default'] = MarkupSection;\n});","define('mobiledoc-kit/models/markup', ['exports', 'mobiledoc-kit/utils/dom-utils', 'mobiledoc-kit/utils/array-utils', 'mobiledoc-kit/models/types', 'mobiledoc-kit/utils/assert'], function (exports, _mobiledocKitUtilsDomUtils, _mobiledocKitUtilsArrayUtils, _mobiledocKitModelsTypes, _mobiledocKitUtilsAssert) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n var VALID_MARKUP_TAGNAMES = ['b', 'i', 'strong', 'em', 'a', 'u', 'sub', // subscript\n 'sup', // superscript\n 's' // strikethrough\n ].map(_mobiledocKitUtilsDomUtils.normalizeTagName);\n\n exports.VALID_MARKUP_TAGNAMES = VALID_MARKUP_TAGNAMES;\n var VALID_ATTRIBUTES = ['href', 'ref'];\n\n exports.VALID_ATTRIBUTES = VALID_ATTRIBUTES;\n\n var Markup = (function () {\n /*\n * @param {Object} attributes key-values\n */\n\n function Markup(tagName) {\n var attributes = arguments.length <= 1 || arguments[1] === undefined ? {} : arguments[1];\n\n _classCallCheck(this, Markup);\n\n this.tagName = (0, _mobiledocKitUtilsDomUtils.normalizeTagName)(tagName);\n\n (0, _mobiledocKitUtilsAssert['default'])('Must use attributes object param (not array) for Markup', !Array.isArray(attributes));\n\n this.attributes = (0, _mobiledocKitUtilsArrayUtils.filterObject)(attributes, VALID_ATTRIBUTES);\n this.type = _mobiledocKitModelsTypes.MARKUP_TYPE;\n\n (0, _mobiledocKitUtilsAssert['default'])('Cannot create markup of tagName ' + tagName, VALID_MARKUP_TAGNAMES.indexOf(this.tagName) !== -1);\n }\n\n _createClass(Markup, [{\n key: 'isForwardInclusive',\n value: function isForwardInclusive() {\n return this.tagName === (0, _mobiledocKitUtilsDomUtils.normalizeTagName)(\"a\") ? false : true;\n }\n }, {\n key: 'isBackwardInclusive',\n value: function isBackwardInclusive() {\n return false;\n }\n }, {\n key: 'hasTag',\n value: function hasTag(tagName) {\n return this.tagName === (0, _mobiledocKitUtilsDomUtils.normalizeTagName)(tagName);\n }\n }, {\n key: 'getAttribute',\n value: function getAttribute(name) {\n return this.attributes[name];\n }\n }], [{\n key: 'isValidElement',\n value: function isValidElement(element) {\n var tagName = (0, _mobiledocKitUtilsDomUtils.normalizeTagName)(element.tagName);\n return VALID_MARKUP_TAGNAMES.indexOf(tagName) !== -1;\n }\n }]);\n\n return Markup;\n })();\n\n exports['default'] = Markup;\n});","define('mobiledoc-kit/models/post-node-builder', ['exports', 'mobiledoc-kit/models/atom', 'mobiledoc-kit/models/post', 'mobiledoc-kit/models/markup-section', 'mobiledoc-kit/models/list-section', 'mobiledoc-kit/models/list-item', 'mobiledoc-kit/models/image', 'mobiledoc-kit/models/marker', 'mobiledoc-kit/models/markup', 'mobiledoc-kit/models/card', 'mobiledoc-kit/utils/dom-utils', 'mobiledoc-kit/utils/array-utils', 'mobiledoc-kit/models/types', 'mobiledoc-kit/utils/assert'], function (exports, _mobiledocKitModelsAtom, _mobiledocKitModelsPost, _mobiledocKitModelsMarkupSection, _mobiledocKitModelsListSection, _mobiledocKitModelsListItem, _mobiledocKitModelsImage, _mobiledocKitModelsMarker, _mobiledocKitModelsMarkup, _mobiledocKitModelsCard, _mobiledocKitUtilsDomUtils, _mobiledocKitUtilsArrayUtils, _mobiledocKitModelsTypes, _mobiledocKitUtilsAssert) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n function cacheKey(tagName, attributes) {\n return (0, _mobiledocKitUtilsDomUtils.normalizeTagName)(tagName) + '-' + (0, _mobiledocKitUtilsArrayUtils.objectToSortedKVArray)(attributes).join('-');\n }\n\n function addMarkupToCache(cache, markup) {\n cache[cacheKey(markup.tagName, markup.attributes)] = markup;\n }\n\n function findMarkupInCache(cache, tagName, attributes) {\n var key = cacheKey(tagName, attributes);\n return cache[key];\n }\n\n /**\n * The PostNodeBuilder is used to create new {@link Post} primitives, such\n * as a MarkupSection, a CardSection, a Markup, etc. Every instance of an\n * {@link Editor} has its own builder instance. The builder can be used\n * inside an {@link Editor#run} callback to programmatically create new\n * Post primitives to insert into the document.\n * A PostNodeBuilder should be read from the Editor, *not* instantiated on its own.\n */\n\n var PostNodeBuilder = (function () {\n /**\n * @private\n */\n\n function PostNodeBuilder() {\n _classCallCheck(this, PostNodeBuilder);\n\n this.markupCache = {};\n }\n\n /**\n * @return {Post} A new, blank post\n */\n\n _createClass(PostNodeBuilder, [{\n key: 'createPost',\n value: function createPost() {\n var sections = arguments.length <= 0 || arguments[0] === undefined ? [] : arguments[0];\n\n var post = new _mobiledocKitModelsPost['default']();\n post.builder = this;\n\n sections.forEach(function (s) {\n return post.sections.append(s);\n });\n\n return post;\n }\n }, {\n key: 'createMarkerableSection',\n value: function createMarkerableSection(type, tagName) {\n var markers = arguments.length <= 2 || arguments[2] === undefined ? [] : arguments[2];\n\n switch (type) {\n case _mobiledocKitModelsTypes.LIST_ITEM_TYPE:\n return this.createListItem(markers);\n case _mobiledocKitModelsTypes.MARKUP_SECTION_TYPE:\n return this.createMarkupSection(tagName, markers);\n default:\n (0, _mobiledocKitUtilsAssert['default'])('Cannot create markerable section of type ' + type, false);\n }\n }\n\n /**\n * @param {tagName} [tagName='P']\n * @param {Marker[]} [markers=[]]\n * @return {MarkupSection}\n */\n }, {\n key: 'createMarkupSection',\n value: function createMarkupSection() {\n var tagName = arguments.length <= 0 || arguments[0] === undefined ? _mobiledocKitModelsMarkupSection.DEFAULT_TAG_NAME : arguments[0];\n var markers = arguments.length <= 1 || arguments[1] === undefined ? [] : arguments[1];\n var isGenerated = arguments.length <= 2 || arguments[2] === undefined ? false : arguments[2];\n\n tagName = (0, _mobiledocKitUtilsDomUtils.normalizeTagName)(tagName);\n var section = new _mobiledocKitModelsMarkupSection['default'](tagName, markers);\n if (isGenerated) {\n section.isGenerated = true;\n }\n section.builder = this;\n return section;\n }\n }, {\n key: 'createListSection',\n value: function createListSection() {\n var tagName = arguments.length <= 0 || arguments[0] === undefined ? _mobiledocKitModelsListSection.DEFAULT_TAG_NAME : arguments[0];\n var items = arguments.length <= 1 || arguments[1] === undefined ? [] : arguments[1];\n\n tagName = (0, _mobiledocKitUtilsDomUtils.normalizeTagName)(tagName);\n var section = new _mobiledocKitModelsListSection['default'](tagName, items);\n section.builder = this;\n return section;\n }\n }, {\n key: 'createListItem',\n value: function createListItem() {\n var markers = arguments.length <= 0 || arguments[0] === undefined ? [] : arguments[0];\n\n var tagName = (0, _mobiledocKitUtilsDomUtils.normalizeTagName)('li');\n var item = new _mobiledocKitModelsListItem['default'](tagName, markers);\n item.builder = this;\n return item;\n }\n }, {\n key: 'createImageSection',\n value: function createImageSection(url) {\n var section = new _mobiledocKitModelsImage['default']();\n if (url) {\n section.src = url;\n }\n return section;\n }\n\n /**\n * @param {String} name\n * @param {Object} [payload={}]\n * @return {CardSection}\n */\n }, {\n key: 'createCardSection',\n value: function createCardSection(name) {\n var payload = arguments.length <= 1 || arguments[1] === undefined ? {} : arguments[1];\n\n var card = new _mobiledocKitModelsCard['default'](name, payload);\n card.builder = this;\n return card;\n }\n\n /**\n * @param {String} value\n * @param {Markup[]} [markups=[]]\n * @return {Marker}\n */\n }, {\n key: 'createMarker',\n value: function createMarker(value) {\n var markups = arguments.length <= 1 || arguments[1] === undefined ? [] : arguments[1];\n\n var marker = new _mobiledocKitModelsMarker['default'](value, markups);\n marker.builder = this;\n return marker;\n }\n\n /**\n * @param {String} name\n * @param {String} [value='']\n * @param {Object} [payload={}]\n * @param {Markup[]} [markups=[]]\n * @return {Atom}\n */\n }, {\n key: 'createAtom',\n value: function createAtom(name) {\n var value = arguments.length <= 1 || arguments[1] === undefined ? '' : arguments[1];\n var payload = arguments.length <= 2 || arguments[2] === undefined ? {} : arguments[2];\n var markups = arguments.length <= 3 || arguments[3] === undefined ? [] : arguments[3];\n\n var atom = new _mobiledocKitModelsAtom['default'](name, value, payload, markups);\n atom.builder = this;\n return atom;\n }\n\n /**\n * @param {String} tagName\n * @param {Object} attributes Key-value pairs of attributes for the markup\n * @return {Markup}\n */\n }, {\n key: 'createMarkup',\n value: function createMarkup(tagName) {\n var attributes = arguments.length <= 1 || arguments[1] === undefined ? {} : arguments[1];\n\n tagName = (0, _mobiledocKitUtilsDomUtils.normalizeTagName)(tagName);\n\n var markup = findMarkupInCache(this.markupCache, tagName, attributes);\n if (!markup) {\n markup = new _mobiledocKitModelsMarkup['default'](tagName, attributes);\n markup.builder = this;\n addMarkupToCache(this.markupCache, markup);\n }\n\n return markup;\n }\n }]);\n\n return PostNodeBuilder;\n })();\n\n exports['default'] = PostNodeBuilder;\n});","define('mobiledoc-kit/models/post', ['exports', 'mobiledoc-kit/models/types', 'mobiledoc-kit/utils/linked-list', 'mobiledoc-kit/utils/array-utils', 'mobiledoc-kit/utils/set', 'mobiledoc-kit/utils/cursor/position', 'mobiledoc-kit/utils/assert'], function (exports, _mobiledocKitModelsTypes, _mobiledocKitUtilsLinkedList, _mobiledocKitUtilsArrayUtils, _mobiledocKitUtilsSet, _mobiledocKitUtilsCursorPosition, _mobiledocKitUtilsAssert) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n /**\n * The Post is an in-memory representation of an editor's document.\n * An editor always has a single post. The post is organized into a list of\n * sections. Each section may be markerable (contains \"markers\", aka editable\n * text) or non-markerable (e.g., a card).\n * When persisting a post, it must first be serialized (loss-lessly) into\n * mobiledoc using {@link Editor#serialize}.\n */\n\n var Post = (function () {\n /**\n * @private\n */\n\n function Post() {\n var _this = this;\n\n _classCallCheck(this, Post);\n\n this.type = _mobiledocKitModelsTypes.POST_TYPE;\n this.sections = new _mobiledocKitUtilsLinkedList['default']({\n adoptItem: function adoptItem(s) {\n return s.post = s.parent = _this;\n },\n freeItem: function freeItem(s) {\n return s.post = s.parent = null;\n }\n });\n }\n\n /**\n * @return {Position} The position at the start of the post (will be a {@link BlankPosition}\n * if the post is blank)\n * @public\n */\n\n _createClass(Post, [{\n key: 'headPosition',\n value: function headPosition() {\n if (this.isBlank) {\n return _mobiledocKitUtilsCursorPosition['default'].blankPosition();\n } else {\n return this.sections.head.headPosition();\n }\n }\n\n /**\n * @return {Position} The position at the end of the post (will be a {@link BlankPosition}\n * if the post is blank)\n * @public\n */\n }, {\n key: 'tailPosition',\n value: function tailPosition() {\n if (this.isBlank) {\n return _mobiledocKitUtilsCursorPosition['default'].blankPosition();\n } else {\n return this.sections.tail.tailPosition();\n }\n }\n\n /**\n * @return {Range} A range encompassing the entire post\n * @public\n */\n }, {\n key: 'toRange',\n value: function toRange() {\n return this.headPosition().toRange(this.tailPosition());\n }\n }, {\n key: 'markersContainedByRange',\n\n /**\n * @param {Range} range\n * @return {Array} markers that are completely contained by the range\n */\n value: function markersContainedByRange(range) {\n var markers = [];\n\n this.walkMarkerableSections(range, function (section) {\n section._markersInRange(range.trimTo(section), function (m, _ref) {\n var isContained = _ref.isContained;\n if (isContained) {\n markers.push(m);\n }\n });\n });\n\n return markers;\n }\n }, {\n key: 'markupsInRange',\n value: function markupsInRange(range) {\n var markups = new _mobiledocKitUtilsSet['default']();\n\n if (range.isCollapsed) {\n var pos = range.head;\n if (pos.isMarkerable) {\n var back = pos.markerIn(-1);\n var forward = pos.markerIn(1);\n\n if (back && forward && back === forward) {\n back.markups.forEach(function (m) {\n return markups.add(m);\n });\n } else {\n (back && back.markups || []).forEach(function (m) {\n if (m.isForwardInclusive()) {\n markups.add(m);\n }\n });\n (forward && forward.markups || []).forEach(function (m) {\n if (m.isBackwardInclusive()) {\n markups.add(m);\n }\n });\n }\n }\n } else {\n this.walkMarkerableSections(range, function (section) {\n (0, _mobiledocKitUtilsArrayUtils.forEach)(section.markupsInRange(range.trimTo(section)), function (m) {\n return markups.add(m);\n });\n });\n }\n\n return markups.toArray();\n }\n }, {\n key: 'walkAllLeafSections',\n value: function walkAllLeafSections(callback) {\n var range = this.headPosition().toRange(this.tailPosition());\n return this.walkLeafSections(range, callback);\n }\n }, {\n key: 'walkLeafSections',\n value: function walkLeafSections(range, callback) {\n var head = range.head;\n var tail = range.tail;\n\n var index = 0;\n var nextSection = undefined,\n shouldStop = undefined;\n var currentSection = head.section;\n\n while (currentSection) {\n nextSection = this._nextLeafSection(currentSection);\n shouldStop = currentSection === tail.section;\n\n callback(currentSection, index);\n index++;\n\n if (shouldStop) {\n break;\n } else {\n currentSection = nextSection;\n }\n }\n }\n }, {\n key: 'walkMarkerableSections',\n value: function walkMarkerableSections(range, callback) {\n this.walkLeafSections(range, function (section) {\n if (section.isMarkerable) {\n callback(section);\n }\n });\n }\n\n // return the next section that has markers after this one,\n // possibly skipping non-markerable sections\n }, {\n key: '_nextLeafSection',\n value: function _nextLeafSection(section) {\n if (!section) {\n return null;\n }\n\n var next = section.next;\n if (next) {\n if (next.isLeafSection) {\n return next;\n } else if (!!next.items) {\n return next.items.head;\n } else {\n (0, _mobiledocKitUtilsAssert['default'])('Cannot determine next section from non-leaf-section', false);\n }\n } else if (section.isNested) {\n // if there is no section after this, but this section is a child\n // (e.g. a ListItem inside a ListSection), check for a markerable\n // section after its parent\n return this._nextLeafSection(section.parent);\n }\n }\n\n /**\n * @param {Range} range\n * @return {Post} A new post, constrained to {range}\n */\n }, {\n key: 'trimTo',\n value: function trimTo(range) {\n var post = this.builder.createPost();\n var builder = this.builder;\n\n var sectionParent = post,\n listParent = null;\n this.walkLeafSections(range, function (section) {\n var newSection = undefined;\n if (section.isMarkerable) {\n if (section.isListItem) {\n if (listParent) {\n sectionParent = null;\n } else {\n listParent = builder.createListSection(section.parent.tagName);\n post.sections.append(listParent);\n sectionParent = null;\n }\n newSection = builder.createListItem();\n listParent.items.append(newSection);\n } else {\n listParent = null;\n sectionParent = post;\n newSection = builder.createMarkupSection(section.tagName);\n }\n\n var currentRange = range.trimTo(section);\n (0, _mobiledocKitUtilsArrayUtils.forEach)(section.markersFor(currentRange.headSectionOffset, currentRange.tailSectionOffset), function (m) {\n return newSection.markers.append(m);\n });\n } else {\n newSection = section.clone();\n }\n if (sectionParent) {\n sectionParent.sections.append(newSection);\n }\n });\n return post;\n }\n }, {\n key: 'isBlank',\n get: function get() {\n return this.sections.isEmpty;\n }\n\n /**\n * If the post has no sections, or only has one, blank section, then it does\n * not have content and this method returns false. Otherwise it is true.\n * @return {Boolean}\n * @public\n */\n }, {\n key: 'hasContent',\n get: function get() {\n if (this.sections.length > 1 || this.sections.length === 1 && !this.sections.head.isBlank) {\n return true;\n } else {\n return false;\n }\n }\n }]);\n\n return Post;\n })();\n\n exports['default'] = Post;\n});","define('mobiledoc-kit/models/render-node', ['exports', 'mobiledoc-kit/utils/linked-item', 'mobiledoc-kit/utils/linked-list', 'mobiledoc-kit/utils/dom-utils', 'mobiledoc-kit/utils/assert'], function (exports, _mobiledocKitUtilsLinkedItem, _mobiledocKitUtilsLinkedList, _mobiledocKitUtilsDomUtils, _mobiledocKitUtilsAssert) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n var _get = function get(_x, _x2, _x3) { var _again = true; _function: while (_again) { var object = _x, property = _x2, receiver = _x3; _again = false; if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { _x = parent; _x2 = property; _x3 = receiver; _again = true; desc = parent = undefined; continue _function; } } else if ('value' in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } } };\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n function _inherits(subClass, superClass) { if (typeof superClass !== 'function' && superClass !== null) { throw new TypeError('Super expression must either be null or a function, not ' + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }\n\n var RenderNode = (function (_LinkedItem) {\n _inherits(RenderNode, _LinkedItem);\n\n function RenderNode(postNode, renderTree) {\n _classCallCheck(this, RenderNode);\n\n _get(Object.getPrototypeOf(RenderNode.prototype), 'constructor', this).call(this);\n this.parent = null;\n this.isDirty = true;\n this.isRemoved = false;\n this.postNode = postNode;\n this._childNodes = null;\n this._element = null;\n this._cursorElement = null; // blank render nodes need a cursor element\n this.renderTree = renderTree;\n\n // RenderNodes for Markers keep track of their markupElement\n this.markupElement = null;\n\n // RenderNodes for Atoms use these properties\n this.headTextNode = null;\n this.tailTextNode = null;\n this.atomNode = null;\n\n // RenderNodes for cards use this property\n this.cardNode = null;\n }\n\n _createClass(RenderNode, [{\n key: 'isAttached',\n value: function isAttached() {\n (0, _mobiledocKitUtilsAssert['default'])('Cannot check if a renderNode is attached without an element.', !!this.element);\n return (0, _mobiledocKitUtilsDomUtils.containsNode)(this.renderTree.rootElement, this.element);\n }\n }, {\n key: 'scheduleForRemoval',\n value: function scheduleForRemoval() {\n this.isRemoved = true;\n if (this.parent) {\n this.parent.markDirty();\n }\n }\n }, {\n key: 'markDirty',\n value: function markDirty() {\n this.isDirty = true;\n if (this.parent) {\n this.parent.markDirty();\n }\n }\n }, {\n key: 'markClean',\n value: function markClean() {\n this.isDirty = false;\n }\n }, {\n key: 'destroy',\n value: function destroy() {\n this.element = null;\n this.parent = null;\n this.postNode = null;\n this.renderTree = null;\n }\n }, {\n key: 'reparsesMutationOfChildNode',\n value: function reparsesMutationOfChildNode(node) {\n if (this.postNode.isCardSection) {\n return !(0, _mobiledocKitUtilsDomUtils.containsNode)(this.cardNode.element, node);\n } else if (this.postNode.isAtom) {\n return !(0, _mobiledocKitUtilsDomUtils.containsNode)(this.atomNode.element, node);\n }\n return true;\n }\n }, {\n key: 'childNodes',\n get: function get() {\n var _this = this;\n\n if (!this._childNodes) {\n this._childNodes = new _mobiledocKitUtilsLinkedList['default']({\n adoptItem: function adoptItem(item) {\n return item.parent = _this;\n },\n freeItem: function freeItem(item) {\n return item.destroy();\n }\n });\n }\n return this._childNodes;\n }\n }, {\n key: 'isRendered',\n get: function get() {\n return !!this.element;\n }\n }, {\n key: 'element',\n set: function set(element) {\n var currentElement = this._element;\n this._element = element;\n\n if (currentElement) {\n this.renderTree.removeElementRenderNode(currentElement);\n }\n\n if (element) {\n this.renderTree.setElementRenderNode(element, this);\n }\n },\n get: function get() {\n return this._element;\n }\n }, {\n key: 'cursorElement',\n set: function set(cursorElement) {\n this._cursorElement = cursorElement;\n },\n get: function get() {\n return this._cursorElement || this.element;\n }\n }]);\n\n return RenderNode;\n })(_mobiledocKitUtilsLinkedItem['default']);\n\n exports['default'] = RenderNode;\n});","define('mobiledoc-kit/models/render-tree', ['exports', 'mobiledoc-kit/models/render-node', 'mobiledoc-kit/utils/element-map'], function (exports, _mobiledocKitModelsRenderNode, _mobiledocKitUtilsElementMap) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n var RenderTree = (function () {\n function RenderTree(rootPostNode) {\n _classCallCheck(this, RenderTree);\n\n this._rootNode = this.buildRenderNode(rootPostNode);\n this._elements = new _mobiledocKitUtilsElementMap['default']();\n }\n\n /*\n * @return {RenderNode} The root render node in this tree\n */\n\n _createClass(RenderTree, [{\n key: 'getElementRenderNode',\n\n /*\n * @param {DOMNode} element\n * @return {RenderNode} The renderNode for this element, if any\n */\n value: function getElementRenderNode(element) {\n return this._elements.get(element);\n }\n }, {\n key: 'setElementRenderNode',\n value: function setElementRenderNode(element, renderNode) {\n this._elements.set(element, renderNode);\n }\n }, {\n key: 'removeElementRenderNode',\n value: function removeElementRenderNode(element) {\n this._elements.remove(element);\n }\n\n /**\n * @param {DOMNode} element\n * Walk up from the dom element until we find a renderNode element\n */\n }, {\n key: 'findRenderNodeFromElement',\n value: function findRenderNodeFromElement(element) {\n var conditionFn = arguments.length <= 1 || arguments[1] === undefined ? function () {\n return true;\n } : arguments[1];\n\n var renderNode = undefined;\n while (element) {\n renderNode = this.getElementRenderNode(element);\n if (renderNode && conditionFn(renderNode)) {\n return renderNode;\n }\n\n // continue loop\n element = element.parentNode;\n\n // stop if we are at the root element\n if (element === this.rootElement) {\n if (conditionFn(this.rootNode)) {\n return this.rootNode;\n } else {\n return;\n }\n }\n }\n }\n }, {\n key: 'buildRenderNode',\n value: function buildRenderNode(postNode) {\n var renderNode = new _mobiledocKitModelsRenderNode['default'](postNode, this);\n postNode.renderNode = renderNode;\n return renderNode;\n }\n }, {\n key: 'rootNode',\n get: function get() {\n return this._rootNode;\n }\n\n /**\n * @return {Boolean}\n */\n }, {\n key: 'isDirty',\n get: function get() {\n return this.rootNode && this.rootNode.isDirty;\n }\n\n /*\n * @return {DOMNode} The root DOM element in this tree\n */\n }, {\n key: 'rootElement',\n get: function get() {\n return this.rootNode.element;\n }\n }]);\n\n return RenderTree;\n })();\n\n exports['default'] = RenderTree;\n});","define('mobiledoc-kit/models/types', ['exports'], function (exports) {\n 'use strict';\n\n var MARKUP_SECTION_TYPE = 'markup-section';\n exports.MARKUP_SECTION_TYPE = MARKUP_SECTION_TYPE;\n var LIST_SECTION_TYPE = 'list-section';\n exports.LIST_SECTION_TYPE = LIST_SECTION_TYPE;\n var MARKUP_TYPE = 'markup';\n exports.MARKUP_TYPE = MARKUP_TYPE;\n var MARKER_TYPE = 'marker';\n exports.MARKER_TYPE = MARKER_TYPE;\n var POST_TYPE = 'post';\n exports.POST_TYPE = POST_TYPE;\n var LIST_ITEM_TYPE = 'list-item';\n exports.LIST_ITEM_TYPE = LIST_ITEM_TYPE;\n var CARD_TYPE = 'card-section';\n exports.CARD_TYPE = CARD_TYPE;\n var IMAGE_SECTION_TYPE = 'image-section';\n exports.IMAGE_SECTION_TYPE = IMAGE_SECTION_TYPE;\n var ATOM_TYPE = 'atom';\n exports.ATOM_TYPE = ATOM_TYPE;\n});","define('mobiledoc-kit/parsers/dom', ['exports', 'mobiledoc-kit/renderers/editor-dom', 'mobiledoc-kit/models/types', 'mobiledoc-kit/utils/dom-utils', 'mobiledoc-kit/utils/array-utils', 'mobiledoc-kit/utils/characters', 'mobiledoc-kit/parsers/section', 'mobiledoc-kit/models/markup'], function (exports, _mobiledocKitRenderersEditorDom, _mobiledocKitModelsTypes, _mobiledocKitUtilsDomUtils, _mobiledocKitUtilsArrayUtils, _mobiledocKitUtilsCharacters, _mobiledocKitParsersSection, _mobiledocKitModelsMarkup) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n exports.transformHTMLText = transformHTMLText;\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n var GOOGLE_DOCS_CONTAINER_ID_REGEX = /^docs\\-internal\\-guid/;\n\n var NO_BREAK_SPACE_REGEX = new RegExp(_mobiledocKitRenderersEditorDom.NO_BREAK_SPACE, 'g');\n var TAB_CHARACTER_REGEX = new RegExp(_mobiledocKitRenderersEditorDom.TAB_CHARACTER, 'g');\n\n function transformHTMLText(textContent) {\n var text = textContent;\n text = text.replace(NO_BREAK_SPACE_REGEX, ' ');\n text = text.replace(TAB_CHARACTER_REGEX, _mobiledocKitUtilsCharacters.TAB);\n return text;\n }\n\n function isGoogleDocsContainer(element) {\n return !(0, _mobiledocKitUtilsDomUtils.isTextNode)(element) && !(0, _mobiledocKitUtilsDomUtils.isCommentNode)(element) && (0, _mobiledocKitUtilsDomUtils.normalizeTagName)(element.tagName) === (0, _mobiledocKitUtilsDomUtils.normalizeTagName)('b') && GOOGLE_DOCS_CONTAINER_ID_REGEX.test(element.id);\n }\n\n function detectRootElement(element) {\n var childNodes = element.childNodes || [];\n var googleDocsContainer = (0, _mobiledocKitUtilsArrayUtils.detect)(childNodes, isGoogleDocsContainer);\n\n if (googleDocsContainer) {\n return googleDocsContainer;\n } else {\n return element;\n }\n }\n\n var TAG_REMAPPING = {\n 'b': 'strong',\n 'i': 'em'\n };\n\n function remapTagName(tagName) {\n var normalized = (0, _mobiledocKitUtilsDomUtils.normalizeTagName)(tagName);\n var remapped = TAG_REMAPPING[normalized];\n return remapped || normalized;\n }\n\n function trim(str) {\n return str.replace(/^\\s+/, '').replace(/\\s+$/, '');\n }\n\n function walkMarkerableNodes(parent, callback) {\n var currentNode = parent;\n\n if ((0, _mobiledocKitUtilsDomUtils.isTextNode)(currentNode) || (0, _mobiledocKitUtilsDomUtils.isElementNode)(currentNode) && currentNode.classList.contains(_mobiledocKitRenderersEditorDom.ATOM_CLASS_NAME)) {\n callback(currentNode);\n } else {\n currentNode = currentNode.firstChild;\n while (currentNode) {\n walkMarkerableNodes(currentNode, callback);\n currentNode = currentNode.nextSibling;\n }\n }\n }\n\n /**\n * Parses DOM element -> Post\n * @private\n */\n\n var DOMParser = (function () {\n function DOMParser(builder) {\n var options = arguments.length <= 1 || arguments[1] === undefined ? {} : arguments[1];\n\n _classCallCheck(this, DOMParser);\n\n this.builder = builder;\n this.sectionParser = new _mobiledocKitParsersSection['default'](this.builder, options);\n }\n\n _createClass(DOMParser, [{\n key: 'parse',\n value: function parse(element) {\n var _this = this;\n\n var post = this.builder.createPost();\n var rootElement = detectRootElement(element);\n\n this._eachChildNode(rootElement, function (child) {\n var sections = _this.parseSections(child);\n _this.appendSections(post, sections);\n });\n\n return post;\n }\n }, {\n key: 'appendSections',\n value: function appendSections(post, sections) {\n var _this2 = this;\n\n (0, _mobiledocKitUtilsArrayUtils.forEach)(sections, function (section) {\n return _this2.appendSection(post, section);\n });\n }\n }, {\n key: 'appendSection',\n value: function appendSection(post, section) {\n if (section.isBlank || section.isMarkerable && trim(section.text) === '') {\n return;\n }\n\n var lastSection = post.sections.tail;\n if (lastSection && lastSection._inferredTagName && section._inferredTagName && lastSection.tagName === section.tagName) {\n lastSection.join(section);\n } else {\n post.sections.append(section);\n }\n }\n }, {\n key: '_eachChildNode',\n value: function _eachChildNode(element, callback) {\n var nodes = (0, _mobiledocKitUtilsDomUtils.isTextNode)(element) ? [element] : element.childNodes;\n (0, _mobiledocKitUtilsArrayUtils.forEach)(nodes, function (node) {\n return callback(node);\n });\n }\n }, {\n key: 'parseSections',\n value: function parseSections(element) {\n return this.sectionParser.parse(element);\n }\n\n // walk up from the textNode until the rootNode, converting each\n // parentNode into a markup\n }, {\n key: 'collectMarkups',\n value: function collectMarkups(textNode, rootNode) {\n var markups = [];\n var currentNode = textNode.parentNode;\n while (currentNode && currentNode !== rootNode) {\n var markup = this.markupFromNode(currentNode);\n if (markup) {\n markups.push(markup);\n }\n\n currentNode = currentNode.parentNode;\n }\n return markups;\n }\n\n // Turn an element node into a markup\n }, {\n key: 'markupFromNode',\n value: function markupFromNode(node) {\n if (_mobiledocKitModelsMarkup['default'].isValidElement(node)) {\n var tagName = remapTagName(node.tagName);\n var attributes = (0, _mobiledocKitUtilsDomUtils.getAttributes)(node);\n return this.builder.createMarkup(tagName, attributes);\n }\n }\n\n // FIXME should move to the section parser?\n // FIXME the `collectMarkups` logic could simplify the section parser?\n }, {\n key: 'reparseSection',\n value: function reparseSection(section, renderTree) {\n switch (section.type) {\n case _mobiledocKitModelsTypes.LIST_SECTION_TYPE:\n return this.reparseListSection(section, renderTree);\n case _mobiledocKitModelsTypes.LIST_ITEM_TYPE:\n return this.reparseListItem(section, renderTree);\n case _mobiledocKitModelsTypes.MARKUP_SECTION_TYPE:\n return this.reparseMarkupSection(section, renderTree);\n default:\n return; // can only parse the above types\n }\n }\n }, {\n key: 'reparseMarkupSection',\n value: function reparseMarkupSection(section, renderTree) {\n return this._reparseSectionContainingMarkers(section, renderTree);\n }\n }, {\n key: 'reparseListItem',\n value: function reparseListItem(listItem, renderTree) {\n return this._reparseSectionContainingMarkers(listItem, renderTree);\n }\n }, {\n key: 'reparseListSection',\n value: function reparseListSection(listSection, renderTree) {\n var _this3 = this;\n\n listSection.items.forEach(function (li) {\n return _this3.reparseListItem(li, renderTree);\n });\n }\n }, {\n key: '_reparseSectionContainingMarkers',\n value: function _reparseSectionContainingMarkers(section, renderTree) {\n var _this4 = this;\n\n var element = section.renderNode.element;\n var seenRenderNodes = [];\n var previousMarker = undefined;\n\n walkMarkerableNodes(element, function (node) {\n var marker = undefined;\n var renderNode = renderTree.getElementRenderNode(node);\n if (renderNode) {\n if (renderNode.postNode.isMarker) {\n var text = transformHTMLText(node.textContent);\n var markups = _this4.collectMarkups(node, element);\n if (text.length) {\n marker = renderNode.postNode;\n marker.value = text;\n marker.markups = markups;\n } else {\n renderNode.scheduleForRemoval();\n }\n } else if (renderNode.postNode.isAtom) {\n var _renderNode = renderNode;\n var headTextNode = _renderNode.headTextNode;\n var tailTextNode = _renderNode.tailTextNode;\n\n if (headTextNode.textContent !== _mobiledocKitRenderersEditorDom.ZWNJ) {\n var value = headTextNode.textContent.replace(new RegExp(_mobiledocKitRenderersEditorDom.ZWNJ, 'g'), '');\n headTextNode.textContent = _mobiledocKitRenderersEditorDom.ZWNJ;\n if (previousMarker && previousMarker.isMarker) {\n previousMarker.value += value;\n if (previousMarker.renderNode) {\n previousMarker.renderNode.markDirty();\n }\n } else {\n var postNode = renderNode.postNode;\n var newMarkups = postNode.markups.slice();\n var newPreviousMarker = _this4.builder.createMarker(value, newMarkups);\n section.markers.insertBefore(newPreviousMarker, postNode);\n\n var newPreviousRenderNode = renderTree.buildRenderNode(newPreviousMarker);\n newPreviousRenderNode.markDirty();\n section.renderNode.markDirty();\n\n seenRenderNodes.push(newPreviousRenderNode);\n section.renderNode.childNodes.insertBefore(newPreviousRenderNode, renderNode);\n }\n }\n if (tailTextNode.textContent !== _mobiledocKitRenderersEditorDom.ZWNJ) {\n var value = tailTextNode.textContent.replace(new RegExp(_mobiledocKitRenderersEditorDom.ZWNJ, 'g'), '');\n tailTextNode.textContent = _mobiledocKitRenderersEditorDom.ZWNJ;\n\n if (renderNode.postNode.next && renderNode.postNode.next.isMarker) {\n var nextMarker = renderNode.postNode.next;\n\n if (nextMarker.renderNode) {\n var nextValue = nextMarker.renderNode.element.textContent;\n nextMarker.renderNode.element.textContent = value + nextValue;\n } else {\n var nextValue = value + nextMarker.value;\n nextMarker.value = nextValue;\n }\n } else {\n var postNode = renderNode.postNode;\n var newMarkups = postNode.markups.slice();\n var newMarker = _this4.builder.createMarker(value, newMarkups);\n\n section.markers.insertAfter(newMarker, postNode);\n\n var newRenderNode = renderTree.buildRenderNode(newMarker);\n seenRenderNodes.push(newRenderNode);\n\n newRenderNode.markDirty();\n section.renderNode.markDirty();\n\n section.renderNode.childNodes.insertAfter(newRenderNode, renderNode);\n }\n }\n if (renderNode) {\n marker = renderNode.postNode;\n }\n }\n } else if ((0, _mobiledocKitUtilsDomUtils.isTextNode)(node)) {\n var text = transformHTMLText(node.textContent);\n var markups = _this4.collectMarkups(node, element);\n marker = _this4.builder.createMarker(text, markups);\n\n renderNode = renderTree.buildRenderNode(marker);\n renderNode.element = node;\n renderNode.markClean();\n section.renderNode.markDirty();\n\n var previousRenderNode = previousMarker && previousMarker.renderNode;\n section.markers.insertAfter(marker, previousMarker);\n section.renderNode.childNodes.insertAfter(renderNode, previousRenderNode);\n }\n\n if (renderNode) {\n seenRenderNodes.push(renderNode);\n }\n previousMarker = marker;\n });\n\n var renderNode = section.renderNode.childNodes.head;\n while (renderNode) {\n if (seenRenderNodes.indexOf(renderNode) === -1) {\n renderNode.scheduleForRemoval();\n }\n renderNode = renderNode.next;\n }\n }\n }]);\n\n return DOMParser;\n })();\n\n exports['default'] = DOMParser;\n});","define('mobiledoc-kit/parsers/html', ['exports', 'mobiledoc-kit/utils/dom-utils', 'mobiledoc-kit/utils/assert', 'mobiledoc-kit/parsers/dom'], function (exports, _mobiledocKitUtilsDomUtils, _mobiledocKitUtilsAssert, _mobiledocKitParsersDom) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n var HTMLParser = (function () {\n function HTMLParser(builder) {\n var options = arguments.length <= 1 || arguments[1] === undefined ? {} : arguments[1];\n\n _classCallCheck(this, HTMLParser);\n\n (0, _mobiledocKitUtilsAssert['default'])('Must pass builder to HTMLParser', builder);\n this.builder = builder;\n this.options = options;\n }\n\n /**\n * @param {String} html to parse\n * @return {Post} A post abstract\n */\n\n _createClass(HTMLParser, [{\n key: 'parse',\n value: function parse(html) {\n var dom = (0, _mobiledocKitUtilsDomUtils.parseHTML)(html);\n var parser = new _mobiledocKitParsersDom['default'](this.builder, this.options);\n return parser.parse(dom);\n }\n }]);\n\n return HTMLParser;\n })();\n\n exports['default'] = HTMLParser;\n});","define('mobiledoc-kit/parsers/mobiledoc/0-2', ['exports', 'mobiledoc-kit/renderers/mobiledoc/0-2', 'mobiledoc-kit/utils/array-utils', 'mobiledoc-kit/utils/assert'], function (exports, _mobiledocKitRenderersMobiledoc02, _mobiledocKitUtilsArrayUtils, _mobiledocKitUtilsAssert) {\n 'use strict';\n\n var _slicedToArray = (function () { function sliceIterator(arr, i) { var _arr = []; var _n = true; var _d = false; var _e = undefined; try { for (var _i = arr[Symbol.iterator](), _s; !(_n = (_s = _i.next()).done); _n = true) { _arr.push(_s.value); if (i && _arr.length === i) break; } } catch (err) { _d = true; _e = err; } finally { try { if (!_n && _i['return']) _i['return'](); } finally { if (_d) throw _e; } } return _arr; } return function (arr, i) { if (Array.isArray(arr)) { return arr; } else if (Symbol.iterator in Object(arr)) { return sliceIterator(arr, i); } else { throw new TypeError('Invalid attempt to destructure non-iterable instance'); } }; })();\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n /*\n * Parses from mobiledoc -> post\n */\n\n var MobiledocParser = (function () {\n function MobiledocParser(builder) {\n _classCallCheck(this, MobiledocParser);\n\n this.builder = builder;\n }\n\n /**\n * @param {Mobiledoc}\n * @return {Post}\n */\n\n _createClass(MobiledocParser, [{\n key: 'parse',\n value: function parse(_ref) {\n var version = _ref.version;\n var sectionData = _ref.sections;\n\n try {\n var markerTypes = sectionData[0];\n var sections = sectionData[1];\n\n var post = this.builder.createPost();\n\n this.markups = [];\n this.markerTypes = this.parseMarkerTypes(markerTypes);\n this.parseSections(sections, post);\n\n return post;\n } catch (e) {\n (0, _mobiledocKitUtilsAssert['default'])('Unable to parse mobiledoc: ' + e.message, false);\n }\n }\n }, {\n key: 'parseMarkerTypes',\n value: function parseMarkerTypes(markerTypes) {\n var _this = this;\n\n return markerTypes.map(function (markerType) {\n return _this.parseMarkerType(markerType);\n });\n }\n }, {\n key: 'parseMarkerType',\n value: function parseMarkerType(_ref2) {\n var _ref22 = _slicedToArray(_ref2, 2);\n\n var tagName = _ref22[0];\n var attributesArray = _ref22[1];\n\n var attributesObject = (0, _mobiledocKitUtilsArrayUtils.kvArrayToObject)(attributesArray || []);\n return this.builder.createMarkup(tagName, attributesObject);\n }\n }, {\n key: 'parseSections',\n value: function parseSections(sections, post) {\n var _this2 = this;\n\n sections.forEach(function (section) {\n return _this2.parseSection(section, post);\n });\n }\n }, {\n key: 'parseSection',\n value: function parseSection(section, post) {\n var _section = _slicedToArray(section, 1);\n\n var type = _section[0];\n\n switch (type) {\n case _mobiledocKitRenderersMobiledoc02.MOBILEDOC_MARKUP_SECTION_TYPE:\n this.parseMarkupSection(section, post);\n break;\n case _mobiledocKitRenderersMobiledoc02.MOBILEDOC_IMAGE_SECTION_TYPE:\n this.parseImageSection(section, post);\n break;\n case _mobiledocKitRenderersMobiledoc02.MOBILEDOC_CARD_SECTION_TYPE:\n this.parseCardSection(section, post);\n break;\n case _mobiledocKitRenderersMobiledoc02.MOBILEDOC_LIST_SECTION_TYPE:\n this.parseListSection(section, post);\n break;\n default:\n (0, _mobiledocKitUtilsAssert['default'])('Unexpected section type ' + type, false);\n }\n }\n }, {\n key: 'parseCardSection',\n value: function parseCardSection(_ref3, post) {\n var _ref32 = _slicedToArray(_ref3, 3);\n\n var type = _ref32[0];\n var name = _ref32[1];\n var payload = _ref32[2];\n\n var section = this.builder.createCardSection(name, payload);\n post.sections.append(section);\n }\n }, {\n key: 'parseImageSection',\n value: function parseImageSection(_ref4, post) {\n var _ref42 = _slicedToArray(_ref4, 2);\n\n var type = _ref42[0];\n var src = _ref42[1];\n\n var section = this.builder.createImageSection(src);\n post.sections.append(section);\n }\n }, {\n key: 'parseMarkupSection',\n value: function parseMarkupSection(_ref5, post) {\n var _ref52 = _slicedToArray(_ref5, 3);\n\n var type = _ref52[0];\n var tagName = _ref52[1];\n var markers = _ref52[2];\n\n var section = this.builder.createMarkupSection(tagName);\n post.sections.append(section);\n this.parseMarkers(markers, section);\n // Strip blank markers after they have been created. This ensures any\n // markup they include has been correctly populated.\n (0, _mobiledocKitUtilsArrayUtils.filter)(section.markers, function (m) {\n return m.isBlank;\n }).forEach(function (m) {\n section.markers.remove(m);\n });\n }\n }, {\n key: 'parseListSection',\n value: function parseListSection(_ref6, post) {\n var _ref62 = _slicedToArray(_ref6, 3);\n\n var type = _ref62[0];\n var tagName = _ref62[1];\n var items = _ref62[2];\n\n var section = this.builder.createListSection(tagName);\n post.sections.append(section);\n this.parseListItems(items, section);\n }\n }, {\n key: 'parseListItems',\n value: function parseListItems(items, section) {\n var _this3 = this;\n\n items.forEach(function (i) {\n return _this3.parseListItem(i, section);\n });\n }\n }, {\n key: 'parseListItem',\n value: function parseListItem(markers, section) {\n var item = this.builder.createListItem();\n this.parseMarkers(markers, item);\n section.items.append(item);\n }\n }, {\n key: 'parseMarkers',\n value: function parseMarkers(markers, parent) {\n var _this4 = this;\n\n markers.forEach(function (m) {\n return _this4.parseMarker(m, parent);\n });\n }\n }, {\n key: 'parseMarker',\n value: function parseMarker(_ref7, parent) {\n var _this5 = this;\n\n var _ref72 = _slicedToArray(_ref7, 3);\n\n var markerTypeIndexes = _ref72[0];\n var closeCount = _ref72[1];\n var value = _ref72[2];\n\n markerTypeIndexes.forEach(function (index) {\n _this5.markups.push(_this5.markerTypes[index]);\n });\n var marker = this.builder.createMarker(value, this.markups.slice());\n parent.markers.append(marker);\n this.markups = this.markups.slice(0, this.markups.length - closeCount);\n }\n }]);\n\n return MobiledocParser;\n })();\n\n exports['default'] = MobiledocParser;\n});","define('mobiledoc-kit/parsers/mobiledoc/0-3', ['exports', 'mobiledoc-kit/renderers/mobiledoc/0-3', 'mobiledoc-kit/utils/array-utils', 'mobiledoc-kit/utils/assert'], function (exports, _mobiledocKitRenderersMobiledoc03, _mobiledocKitUtilsArrayUtils, _mobiledocKitUtilsAssert) {\n 'use strict';\n\n var _slicedToArray = (function () { function sliceIterator(arr, i) { var _arr = []; var _n = true; var _d = false; var _e = undefined; try { for (var _i = arr[Symbol.iterator](), _s; !(_n = (_s = _i.next()).done); _n = true) { _arr.push(_s.value); if (i && _arr.length === i) break; } } catch (err) { _d = true; _e = err; } finally { try { if (!_n && _i['return']) _i['return'](); } finally { if (_d) throw _e; } } return _arr; } return function (arr, i) { if (Array.isArray(arr)) { return arr; } else if (Symbol.iterator in Object(arr)) { return sliceIterator(arr, i); } else { throw new TypeError('Invalid attempt to destructure non-iterable instance'); } }; })();\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n /*\n * Parses from mobiledoc -> post\n */\n\n var MobiledocParser = (function () {\n function MobiledocParser(builder) {\n _classCallCheck(this, MobiledocParser);\n\n this.builder = builder;\n }\n\n /**\n * @param {Mobiledoc}\n * @return {Post}\n */\n\n _createClass(MobiledocParser, [{\n key: 'parse',\n value: function parse(_ref) {\n var version = _ref.version;\n var sections = _ref.sections;\n var markerTypes = _ref.markups;\n var cardTypes = _ref.cards;\n var atomTypes = _ref.atoms;\n\n try {\n var post = this.builder.createPost();\n\n this.markups = [];\n this.markerTypes = this.parseMarkerTypes(markerTypes);\n this.cardTypes = this.parseCardTypes(cardTypes);\n this.atomTypes = this.parseAtomTypes(atomTypes);\n this.parseSections(sections, post);\n\n return post;\n } catch (e) {\n (0, _mobiledocKitUtilsAssert['default'])('Unable to parse mobiledoc: ' + e.message, false);\n }\n }\n }, {\n key: 'parseMarkerTypes',\n value: function parseMarkerTypes(markerTypes) {\n var _this = this;\n\n return markerTypes.map(function (markerType) {\n return _this.parseMarkerType(markerType);\n });\n }\n }, {\n key: 'parseMarkerType',\n value: function parseMarkerType(_ref2) {\n var _ref22 = _slicedToArray(_ref2, 2);\n\n var tagName = _ref22[0];\n var attributesArray = _ref22[1];\n\n var attributesObject = (0, _mobiledocKitUtilsArrayUtils.kvArrayToObject)(attributesArray || []);\n return this.builder.createMarkup(tagName, attributesObject);\n }\n }, {\n key: 'parseCardTypes',\n value: function parseCardTypes(cardTypes) {\n var _this2 = this;\n\n return cardTypes.map(function (cardType) {\n return _this2.parseCardType(cardType);\n });\n }\n }, {\n key: 'parseCardType',\n value: function parseCardType(_ref3) {\n var _ref32 = _slicedToArray(_ref3, 2);\n\n var cardName = _ref32[0];\n var cardPayload = _ref32[1];\n\n return [cardName, cardPayload];\n }\n }, {\n key: 'parseAtomTypes',\n value: function parseAtomTypes(atomTypes) {\n var _this3 = this;\n\n return atomTypes.map(function (atomType) {\n return _this3.parseAtomType(atomType);\n });\n }\n }, {\n key: 'parseAtomType',\n value: function parseAtomType(_ref4) {\n var _ref42 = _slicedToArray(_ref4, 3);\n\n var atomName = _ref42[0];\n var atomValue = _ref42[1];\n var atomPayload = _ref42[2];\n\n return [atomName, atomValue, atomPayload];\n }\n }, {\n key: 'parseSections',\n value: function parseSections(sections, post) {\n var _this4 = this;\n\n sections.forEach(function (section) {\n return _this4.parseSection(section, post);\n });\n }\n }, {\n key: 'parseSection',\n value: function parseSection(section, post) {\n var _section = _slicedToArray(section, 1);\n\n var type = _section[0];\n\n switch (type) {\n case _mobiledocKitRenderersMobiledoc03.MOBILEDOC_MARKUP_SECTION_TYPE:\n this.parseMarkupSection(section, post);\n break;\n case _mobiledocKitRenderersMobiledoc03.MOBILEDOC_IMAGE_SECTION_TYPE:\n this.parseImageSection(section, post);\n break;\n case _mobiledocKitRenderersMobiledoc03.MOBILEDOC_CARD_SECTION_TYPE:\n this.parseCardSection(section, post);\n break;\n case _mobiledocKitRenderersMobiledoc03.MOBILEDOC_LIST_SECTION_TYPE:\n this.parseListSection(section, post);\n break;\n default:\n (0, _mobiledocKitUtilsAssert['default'])('Unexpected section type ${type}', false);\n }\n }\n }, {\n key: 'getAtomTypeFromIndex',\n value: function getAtomTypeFromIndex(index) {\n var atomType = this.atomTypes[index];\n (0, _mobiledocKitUtilsAssert['default'])('No atom definition found at index ' + index, !!atomType);\n return atomType;\n }\n }, {\n key: 'getCardTypeFromIndex',\n value: function getCardTypeFromIndex(index) {\n var cardType = this.cardTypes[index];\n (0, _mobiledocKitUtilsAssert['default'])('No card definition found at index ' + index, !!cardType);\n return cardType;\n }\n }, {\n key: 'parseCardSection',\n value: function parseCardSection(_ref5, post) {\n var _ref52 = _slicedToArray(_ref5, 2);\n\n var type = _ref52[0];\n var cardIndex = _ref52[1];\n\n var _getCardTypeFromIndex = this.getCardTypeFromIndex(cardIndex);\n\n var _getCardTypeFromIndex2 = _slicedToArray(_getCardTypeFromIndex, 2);\n\n var name = _getCardTypeFromIndex2[0];\n var payload = _getCardTypeFromIndex2[1];\n\n var section = this.builder.createCardSection(name, payload);\n post.sections.append(section);\n }\n }, {\n key: 'parseImageSection',\n value: function parseImageSection(_ref6, post) {\n var _ref62 = _slicedToArray(_ref6, 2);\n\n var type = _ref62[0];\n var src = _ref62[1];\n\n var section = this.builder.createImageSection(src);\n post.sections.append(section);\n }\n }, {\n key: 'parseMarkupSection',\n value: function parseMarkupSection(_ref7, post) {\n var _ref72 = _slicedToArray(_ref7, 3);\n\n var type = _ref72[0];\n var tagName = _ref72[1];\n var markers = _ref72[2];\n\n var section = this.builder.createMarkupSection(tagName);\n post.sections.append(section);\n this.parseMarkers(markers, section);\n // Strip blank markers after they have been created. This ensures any\n // markup they include has been correctly populated.\n (0, _mobiledocKitUtilsArrayUtils.filter)(section.markers, function (m) {\n return m.isBlank;\n }).forEach(function (m) {\n section.markers.remove(m);\n });\n }\n }, {\n key: 'parseListSection',\n value: function parseListSection(_ref8, post) {\n var _ref82 = _slicedToArray(_ref8, 3);\n\n var type = _ref82[0];\n var tagName = _ref82[1];\n var items = _ref82[2];\n\n var section = this.builder.createListSection(tagName);\n post.sections.append(section);\n this.parseListItems(items, section);\n }\n }, {\n key: 'parseListItems',\n value: function parseListItems(items, section) {\n var _this5 = this;\n\n items.forEach(function (i) {\n return _this5.parseListItem(i, section);\n });\n }\n }, {\n key: 'parseListItem',\n value: function parseListItem(markers, section) {\n var item = this.builder.createListItem();\n this.parseMarkers(markers, item);\n section.items.append(item);\n }\n }, {\n key: 'parseMarkers',\n value: function parseMarkers(markers, parent) {\n var _this6 = this;\n\n markers.forEach(function (m) {\n return _this6.parseMarker(m, parent);\n });\n }\n }, {\n key: 'parseMarker',\n value: function parseMarker(_ref9, parent) {\n var _this7 = this;\n\n var _ref92 = _slicedToArray(_ref9, 4);\n\n var type = _ref92[0];\n var markerTypeIndexes = _ref92[1];\n var closeCount = _ref92[2];\n var value = _ref92[3];\n\n markerTypeIndexes.forEach(function (index) {\n _this7.markups.push(_this7.markerTypes[index]);\n });\n\n var marker = this.buildMarkerType(type, value);\n parent.markers.append(marker);\n\n this.markups = this.markups.slice(0, this.markups.length - closeCount);\n }\n }, {\n key: 'buildMarkerType',\n value: function buildMarkerType(type, value) {\n switch (type) {\n case _mobiledocKitRenderersMobiledoc03.MOBILEDOC_MARKUP_MARKER_TYPE:\n return this.builder.createMarker(value, this.markups.slice());\n case _mobiledocKitRenderersMobiledoc03.MOBILEDOC_ATOM_MARKER_TYPE:\n var _getAtomTypeFromIndex = this.getAtomTypeFromIndex(value),\n _getAtomTypeFromIndex2 = _slicedToArray(_getAtomTypeFromIndex, 3),\n atomName = _getAtomTypeFromIndex2[0],\n atomValue = _getAtomTypeFromIndex2[1],\n atomPayload = _getAtomTypeFromIndex2[2];\n\n return this.builder.createAtom(atomName, atomValue, atomPayload, this.markups.slice());\n default:\n (0, _mobiledocKitUtilsAssert['default'])('Unexpected marker type ' + type, false);\n }\n }\n }]);\n\n return MobiledocParser;\n })();\n\n exports['default'] = MobiledocParser;\n});","define('mobiledoc-kit/parsers/mobiledoc', ['exports', 'mobiledoc-kit/parsers/mobiledoc/0-2', 'mobiledoc-kit/parsers/mobiledoc/0-3', 'mobiledoc-kit/renderers/mobiledoc/0-2', 'mobiledoc-kit/renderers/mobiledoc/0-3', 'mobiledoc-kit/utils/assert'], function (exports, _mobiledocKitParsersMobiledoc02, _mobiledocKitParsersMobiledoc03, _mobiledocKitRenderersMobiledoc02, _mobiledocKitRenderersMobiledoc03, _mobiledocKitUtilsAssert) {\n 'use strict';\n\n function parseVersion(mobiledoc) {\n return mobiledoc.version;\n }\n\n exports['default'] = {\n parse: function parse(builder, mobiledoc) {\n var version = parseVersion(mobiledoc);\n switch (version) {\n case _mobiledocKitRenderersMobiledoc02.MOBILEDOC_VERSION:\n return new _mobiledocKitParsersMobiledoc02['default'](builder).parse(mobiledoc);\n case _mobiledocKitRenderersMobiledoc03.MOBILEDOC_VERSION:\n return new _mobiledocKitParsersMobiledoc03['default'](builder).parse(mobiledoc);\n default:\n (0, _mobiledocKitUtilsAssert['default'])('Unknown version of mobiledoc parser requested: ' + version, false);\n }\n }\n };\n});","define('mobiledoc-kit/parsers/section', ['exports', 'mobiledoc-kit/models/markup-section', 'mobiledoc-kit/models/list-section', 'mobiledoc-kit/models/list-item', 'mobiledoc-kit/models/types', 'mobiledoc-kit/models/markup', 'mobiledoc-kit/utils/dom-utils', 'mobiledoc-kit/utils/array-utils', 'mobiledoc-kit/parsers/dom', 'mobiledoc-kit/utils/assert'], function (exports, _mobiledocKitModelsMarkupSection, _mobiledocKitModelsListSection, _mobiledocKitModelsListItem, _mobiledocKitModelsTypes, _mobiledocKitModelsMarkup, _mobiledocKitUtilsDomUtils, _mobiledocKitUtilsArrayUtils, _mobiledocKitParsersDom, _mobiledocKitUtilsAssert) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _toConsumableArray(arr) { if (Array.isArray(arr)) { for (var i = 0, arr2 = Array(arr.length); i < arr.length; i++) arr2[i] = arr[i]; return arr2; } else { return Array.from(arr); } }\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n var SKIPPABLE_ELEMENT_TAG_NAMES = ['style', 'head', 'title', 'meta'].map(_mobiledocKitUtilsDomUtils.normalizeTagName);\n\n var NEWLINES = /\\n/g;\n function sanitize(text) {\n text = text.replace(NEWLINES, '');\n return text;\n }\n\n /**\n * parses an element into a section, ignoring any non-markup\n * elements contained within\n * @private\n */\n\n var SectionParser = (function () {\n function SectionParser(builder) {\n var options = arguments.length <= 1 || arguments[1] === undefined ? {} : arguments[1];\n\n _classCallCheck(this, SectionParser);\n\n this.builder = builder;\n this.plugins = options.plugins || [];\n }\n\n _createClass(SectionParser, [{\n key: 'parse',\n value: function parse(element) {\n var _this = this;\n\n if (this._isSkippable(element)) {\n return [];\n }\n this.sections = [];\n this.state = {};\n\n this._updateStateFromElement(element);\n\n var childNodes = (0, _mobiledocKitUtilsDomUtils.isTextNode)(element) ? [element] : element.childNodes;\n\n if (this.state.section.isListSection) {\n this.parseListItems(childNodes);\n } else {\n (0, _mobiledocKitUtilsArrayUtils.forEach)(childNodes, function (el) {\n _this.parseNode(el);\n });\n }\n\n this._closeCurrentSection();\n\n return this.sections;\n }\n }, {\n key: 'parseListItems',\n value: function parseListItems(childNodes) {\n var _this2 = this;\n\n var state = this.state;\n\n (0, _mobiledocKitUtilsArrayUtils.forEach)(childNodes, function (el) {\n var parsed = new _this2.constructor(_this2.builder).parse(el);\n var li = parsed[0];\n if (li && li.isListItem) {\n state.section.items.append(li);\n }\n });\n }\n }, {\n key: 'runPlugins',\n value: function runPlugins(node) {\n var _this3 = this;\n\n var isNodeFinished = false;\n var env = {\n addSection: function addSection(section) {\n _this3._closeCurrentSection();\n _this3.sections.push(section);\n },\n addMarkerable: function addMarkerable(marker) {\n var state = _this3.state;\n var section = state.section;\n\n (0, _mobiledocKitUtilsAssert['default'])('Markerables can only be appended to markup sections and list item sections', section && section.isMarkerable);\n if (state.text) {\n _this3._createMarker();\n }\n section.markers.append(marker);\n },\n nodeFinished: function nodeFinished() {\n isNodeFinished = true;\n }\n };\n for (var i = 0; i < this.plugins.length; i++) {\n var plugin = this.plugins[i];\n plugin(node, this.builder, env);\n if (isNodeFinished) {\n return true;\n }\n }\n return false;\n }\n }, {\n key: 'parseNode',\n value: function parseNode(node) {\n if (!this.state.section) {\n this._updateStateFromElement(node);\n }\n\n var nodeFinished = this.runPlugins(node);\n if (nodeFinished) {\n return;\n }\n\n switch (node.nodeType) {\n case _mobiledocKitUtilsDomUtils.NODE_TYPES.TEXT:\n this.parseTextNode(node);\n break;\n case _mobiledocKitUtilsDomUtils.NODE_TYPES.ELEMENT:\n this.parseElementNode(node);\n break;\n }\n }\n }, {\n key: 'parseElementNode',\n value: function parseElementNode(element) {\n var _state$markups,\n _this4 = this;\n\n var state = this.state;\n\n var markups = this._markupsFromElement(element);\n if (markups.length && state.text.length) {\n this._createMarker();\n }\n (_state$markups = state.markups).push.apply(_state$markups, _toConsumableArray(markups));\n\n (0, _mobiledocKitUtilsArrayUtils.forEach)(element.childNodes, function (node) {\n _this4.parseNode(node);\n });\n\n if (markups.length && state.text.length) {\n // create the marker started for this node\n this._createMarker();\n }\n\n // pop the current markups from the stack\n state.markups.splice(-markups.length, markups.length);\n }\n }, {\n key: 'parseTextNode',\n value: function parseTextNode(textNode) {\n var state = this.state;\n\n state.text += sanitize(textNode.textContent);\n }\n }, {\n key: '_updateStateFromElement',\n value: function _updateStateFromElement(element) {\n var state = this.state;\n\n state.section = this._createSectionFromElement(element);\n state.markups = this._markupsFromElement(element);\n state.text = '';\n }\n }, {\n key: '_closeCurrentSection',\n value: function _closeCurrentSection() {\n var sections = this.sections;\n var state = this.state;\n\n if (!state.section) {\n return;\n }\n\n // close a trailing text node if it exists\n if (state.text.length) {\n this._createMarker();\n }\n\n sections.push(state.section);\n state.section = null;\n }\n }, {\n key: '_markupsFromElement',\n value: function _markupsFromElement(element) {\n var builder = this.builder;\n\n var markups = [];\n if ((0, _mobiledocKitUtilsDomUtils.isTextNode)(element)) {\n return markups;\n }\n\n var tagName = (0, _mobiledocKitUtilsDomUtils.normalizeTagName)(element.tagName);\n if (this._isValidMarkupForElement(tagName, element)) {\n markups.push(builder.createMarkup(tagName, (0, _mobiledocKitUtilsDomUtils.getAttributes)(element)));\n }\n\n this._markupsFromElementStyle(element).forEach(function (markup) {\n return markups.push(markup);\n });\n\n return markups;\n }\n }, {\n key: '_isValidMarkupForElement',\n value: function _isValidMarkupForElement(tagName, element) {\n if (_mobiledocKitModelsMarkup.VALID_MARKUP_TAGNAMES.indexOf(tagName) === -1) {\n return false;\n } else if (tagName === 'b') {\n // google docs add a that should not\n // create a \"b\" markup\n return element.style.fontWeight !== 'normal';\n }\n return true;\n }\n }, {\n key: '_markupsFromElementStyle',\n value: function _markupsFromElementStyle(element) {\n var builder = this.builder;\n\n var markups = [];\n var _element$style = element.style;\n var fontStyle = _element$style.fontStyle;\n var fontWeight = _element$style.fontWeight;\n\n if (fontStyle === 'italic') {\n markups.push(builder.createMarkup('em'));\n }\n if (fontWeight === 'bold' || fontWeight === '700') {\n markups.push(builder.createMarkup('strong'));\n }\n return markups;\n }\n }, {\n key: '_createMarker',\n value: function _createMarker() {\n var state = this.state;\n\n var text = (0, _mobiledocKitParsersDom.transformHTMLText)(state.text);\n var marker = this.builder.createMarker(text, state.markups);\n state.section.markers.append(marker);\n state.text = '';\n }\n }, {\n key: '_getSectionDetails',\n value: function _getSectionDetails(element) {\n var sectionType = undefined,\n tagName = undefined,\n inferredTagName = false;\n if ((0, _mobiledocKitUtilsDomUtils.isTextNode)(element)) {\n tagName = _mobiledocKitModelsMarkupSection.DEFAULT_TAG_NAME;\n sectionType = _mobiledocKitModelsTypes.MARKUP_SECTION_TYPE;\n inferredTagName = true;\n } else {\n tagName = (0, _mobiledocKitUtilsDomUtils.normalizeTagName)(element.tagName);\n\n if ((0, _mobiledocKitUtilsArrayUtils.contains)(_mobiledocKitModelsListSection.VALID_LIST_SECTION_TAGNAMES, tagName)) {\n sectionType = _mobiledocKitModelsTypes.LIST_SECTION_TYPE;\n } else if ((0, _mobiledocKitUtilsArrayUtils.contains)(_mobiledocKitModelsListItem.VALID_LIST_ITEM_TAGNAMES, tagName)) {\n sectionType = _mobiledocKitModelsTypes.LIST_ITEM_TYPE;\n } else if ((0, _mobiledocKitUtilsArrayUtils.contains)(_mobiledocKitModelsMarkupSection.VALID_MARKUP_SECTION_TAGNAMES, tagName)) {\n sectionType = _mobiledocKitModelsTypes.MARKUP_SECTION_TYPE;\n } else {\n sectionType = _mobiledocKitModelsTypes.MARKUP_SECTION_TYPE;\n tagName = _mobiledocKitModelsMarkupSection.DEFAULT_TAG_NAME;\n inferredTagName = true;\n }\n }\n\n return { sectionType: sectionType, tagName: tagName, inferredTagName: inferredTagName };\n }\n }, {\n key: '_createSectionFromElement',\n value: function _createSectionFromElement(element) {\n var builder = this.builder;\n\n var section = undefined;\n\n var _getSectionDetails2 = this._getSectionDetails(element);\n\n var tagName = _getSectionDetails2.tagName;\n var sectionType = _getSectionDetails2.sectionType;\n var inferredTagName = _getSectionDetails2.inferredTagName;\n\n switch (sectionType) {\n case _mobiledocKitModelsTypes.LIST_SECTION_TYPE:\n section = builder.createListSection(tagName);\n break;\n case _mobiledocKitModelsTypes.LIST_ITEM_TYPE:\n section = builder.createListItem();\n break;\n case _mobiledocKitModelsTypes.MARKUP_SECTION_TYPE:\n section = builder.createMarkupSection(tagName);\n section._inferredTagName = inferredTagName;\n break;\n default:\n (0, _mobiledocKitUtilsAssert['default'])('Cannot parse section from element', false);\n }\n\n return section;\n }\n }, {\n key: '_isSkippable',\n value: function _isSkippable(element) {\n return (0, _mobiledocKitUtilsDomUtils.isCommentNode)(element) || element.nodeType === _mobiledocKitUtilsDomUtils.NODE_TYPES.ELEMENT && (0, _mobiledocKitUtilsArrayUtils.contains)(SKIPPABLE_ELEMENT_TAG_NAMES, (0, _mobiledocKitUtilsDomUtils.normalizeTagName)(element.tagName));\n }\n }]);\n\n return SectionParser;\n })();\n\n exports['default'] = SectionParser;\n});","define('mobiledoc-kit/parsers/text', ['exports', 'mobiledoc-kit/utils/assert', 'mobiledoc-kit/models/types', 'mobiledoc-kit/models/markup-section'], function (exports, _mobiledocKitUtilsAssert, _mobiledocKitModelsTypes, _mobiledocKitModelsMarkupSection) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n var UL_LI_REGEX = /^\\* (.*)$/;\n var OL_LI_REGEX = /^\\d\\.? (.*)$/;\n var CR = '\\r';\n var LF = '\\n';\n var CR_REGEX = new RegExp(CR, 'g');\n var CR_LF_REGEX = new RegExp(CR + LF, 'g');\n\n var SECTION_BREAK = LF;\n\n exports.SECTION_BREAK = SECTION_BREAK;\n function normalizeLineEndings(text) {\n return text.replace(CR_LF_REGEX, LF).replace(CR_REGEX, LF);\n }\n\n var TextParser = (function () {\n function TextParser(builder, options) {\n _classCallCheck(this, TextParser);\n\n this.builder = builder;\n this.options = options;\n\n this.post = this.builder.createPost();\n this.prevSection = null;\n }\n\n /**\n * @param {String} text to parse\n * @return {Post} a post abstract\n */\n\n _createClass(TextParser, [{\n key: 'parse',\n value: function parse(text) {\n var _this = this;\n\n text = normalizeLineEndings(text);\n text.split(SECTION_BREAK).forEach(function (text) {\n var section = _this._parseSection(text);\n _this._appendSection(section);\n });\n\n return this.post;\n }\n }, {\n key: '_parseSection',\n value: function _parseSection(text) {\n var tagName = _mobiledocKitModelsMarkupSection.DEFAULT_TAG_NAME,\n type = _mobiledocKitModelsTypes.MARKUP_SECTION_TYPE,\n section = undefined;\n\n if (UL_LI_REGEX.test(text)) {\n tagName = 'ul';\n type = _mobiledocKitModelsTypes.LIST_SECTION_TYPE;\n text = text.match(UL_LI_REGEX)[1];\n } else if (OL_LI_REGEX.test(text)) {\n tagName = 'ol';\n type = _mobiledocKitModelsTypes.LIST_SECTION_TYPE;\n text = text.match(OL_LI_REGEX)[1];\n }\n\n var markers = [this.builder.createMarker(text)];\n\n switch (type) {\n case _mobiledocKitModelsTypes.LIST_SECTION_TYPE:\n var item = this.builder.createListItem(markers);\n var list = this.builder.createListSection(tagName, [item]);\n section = list;\n break;\n case _mobiledocKitModelsTypes.MARKUP_SECTION_TYPE:\n section = this.builder.createMarkupSection(tagName, markers);\n break;\n default:\n (0, _mobiledocKitUtilsAssert['default'])('Unknown type encountered ' + type, false);\n }\n\n return section;\n }\n }, {\n key: '_appendSection',\n value: function _appendSection(section) {\n var _this2 = this;\n\n var isSameListSection = section.isListSection && this.prevSection && this.prevSection.isListSection && this.prevSection.tagName === section.tagName;\n\n if (isSameListSection) {\n section.items.forEach(function (item) {\n _this2.prevSection.items.append(item.clone());\n });\n } else {\n this.post.sections.insertAfter(section, this.prevSection);\n this.prevSection = section;\n }\n }\n }]);\n\n return TextParser;\n })();\n\n exports['default'] = TextParser;\n});","define('mobiledoc-kit/renderers/editor-dom', ['exports', 'mobiledoc-kit/models/card-node', 'mobiledoc-kit/utils/array-utils', 'mobiledoc-kit/models/atom-node', 'mobiledoc-kit/models/types', 'mobiledoc-kit/utils/string-utils', 'mobiledoc-kit/utils/dom-utils', 'mobiledoc-kit/models/markup-section', 'mobiledoc-kit/utils/assert', 'mobiledoc-kit/utils/characters'], function (exports, _mobiledocKitModelsCardNode, _mobiledocKitUtilsArrayUtils, _mobiledocKitModelsAtomNode, _mobiledocKitModelsTypes, _mobiledocKitUtilsStringUtils, _mobiledocKitUtilsDomUtils, _mobiledocKitModelsMarkupSection, _mobiledocKitUtilsAssert, _mobiledocKitUtilsCharacters) {\n 'use strict';\n\n var _destroyHooks;\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _defineProperty(obj, key, value) { if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; }\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n var CARD_ELEMENT_CLASS_NAME = '__mobiledoc-card';\n exports.CARD_ELEMENT_CLASS_NAME = CARD_ELEMENT_CLASS_NAME;\n var NO_BREAK_SPACE = ' ';\n exports.NO_BREAK_SPACE = NO_BREAK_SPACE;\n var TAB_CHARACTER = ' ';\n exports.TAB_CHARACTER = TAB_CHARACTER;\n var SPACE = ' ';\n exports.SPACE = SPACE;\n var ZWNJ = '‌';\n exports.ZWNJ = ZWNJ;\n var ATOM_CLASS_NAME = '-mobiledoc-kit__atom';\n exports.ATOM_CLASS_NAME = ATOM_CLASS_NAME;\n var EDITOR_HAS_NO_CONTENT_CLASS_NAME = '__has-no-content';\n exports.EDITOR_HAS_NO_CONTENT_CLASS_NAME = EDITOR_HAS_NO_CONTENT_CLASS_NAME;\n var EDITOR_ELEMENT_CLASS_NAME = '__mobiledoc-editor';\n\n exports.EDITOR_ELEMENT_CLASS_NAME = EDITOR_ELEMENT_CLASS_NAME;\n function createElementFromMarkup(doc, markup) {\n var element = doc.createElement(markup.tagName);\n Object.keys(markup.attributes).forEach(function (k) {\n element.setAttribute(k, markup.attributes[k]);\n });\n return element;\n }\n\n var TWO_SPACES = '' + SPACE + SPACE;\n var SPACE_AND_NO_BREAK = '' + SPACE + NO_BREAK_SPACE;\n var SPACES_REGEX = new RegExp(TWO_SPACES, 'g');\n var TAB_REGEX = new RegExp(_mobiledocKitUtilsCharacters.TAB, 'g');\n var endsWithSpace = function endsWithSpace(text) {\n return (0, _mobiledocKitUtilsStringUtils.endsWith)(text, SPACE);\n };\n var startsWithSpace = function startsWithSpace(text) {\n return (0, _mobiledocKitUtilsStringUtils.startsWith)(text, SPACE);\n };\n\n // FIXME: This can be done more efficiently with a single pass\n // building a correct string based on the original.\n function renderHTMLText(marker) {\n var text = marker.value;\n text = text.replace(SPACES_REGEX, SPACE_AND_NO_BREAK).replace(TAB_REGEX, TAB_CHARACTER);\n\n // If the first marker has a leading space or the last marker has a\n // trailing space, the browser will collapse the space when we position\n // the cursor.\n // See https://github.com/bustle/mobiledoc-kit/issues/68\n // and https://github.com/bustle/mobiledoc-kit/issues/75\n if (marker.isMarker && endsWithSpace(text) && !marker.next) {\n text = text.substr(0, text.length - 1) + NO_BREAK_SPACE;\n }\n if (marker.isMarker && startsWithSpace(text) && (!marker.prev || marker.prev.isMarker && endsWithSpace(marker.prev.value))) {\n text = NO_BREAK_SPACE + text.substr(1);\n }\n return text;\n }\n\n // ascends from element upward, returning the last parent node that is not\n // parentElement\n function penultimateParentOf(element, parentElement) {\n while (parentElement && element.parentNode !== parentElement && element.parentNode !== document.body // ensure the while loop stops\n ) {\n element = element.parentNode;\n }\n return element;\n }\n\n function renderMarkupSection(section) {\n var element = undefined;\n if (_mobiledocKitModelsMarkupSection.MARKUP_SECTION_ELEMENT_NAMES.indexOf(section.tagName) !== -1) {\n element = document.createElement(section.tagName);\n } else {\n element = document.createElement('div');\n (0, _mobiledocKitUtilsDomUtils.addClassName)(element, section.tagName);\n }\n\n return element;\n }\n\n function renderListSection(section) {\n return document.createElement(section.tagName);\n }\n\n function renderListItem() {\n return document.createElement('li');\n }\n\n function renderCursorPlaceholder() {\n return document.createElement('br');\n }\n\n function renderInlineCursorPlaceholder() {\n return document.createTextNode(ZWNJ);\n }\n\n function renderCard() {\n var wrapper = document.createElement('div');\n var cardElement = document.createElement('div');\n cardElement.contentEditable = false;\n (0, _mobiledocKitUtilsDomUtils.addClassName)(cardElement, CARD_ELEMENT_CLASS_NAME);\n wrapper.appendChild(renderInlineCursorPlaceholder());\n wrapper.appendChild(cardElement);\n wrapper.appendChild(renderInlineCursorPlaceholder());\n return { wrapper: wrapper, cardElement: cardElement };\n }\n\n /**\n * Wrap the element in all of the opened markups\n * @return {DOMElement} the wrapped element\n * @private\n */\n function wrapElement(element, openedMarkups) {\n var wrappedElement = element;\n\n for (var i = openedMarkups.length - 1; i >= 0; i--) {\n var markup = openedMarkups[i];\n var openedElement = createElementFromMarkup(document, markup);\n openedElement.appendChild(wrappedElement);\n wrappedElement = openedElement;\n }\n\n return wrappedElement;\n }\n\n // Attach the element to its parent element at the correct position based on the\n // previousRenderNode\n function attachElementToParent(element, parentElement) {\n var previousRenderNode = arguments.length <= 2 || arguments[2] === undefined ? null : arguments[2];\n\n if (previousRenderNode) {\n var previousSibling = previousRenderNode.element;\n var previousSiblingPenultimate = penultimateParentOf(previousSibling, parentElement);\n parentElement.insertBefore(element, previousSiblingPenultimate.nextSibling);\n } else {\n parentElement.insertBefore(element, parentElement.firstChild);\n }\n }\n\n function renderAtom(atom, element, previousRenderNode) {\n var atomElement = document.createElement('span');\n atomElement.contentEditable = false;\n\n var wrapper = document.createElement('span');\n (0, _mobiledocKitUtilsDomUtils.addClassName)(wrapper, ATOM_CLASS_NAME);\n var headTextNode = renderInlineCursorPlaceholder();\n var tailTextNode = renderInlineCursorPlaceholder();\n\n wrapper.appendChild(headTextNode);\n wrapper.appendChild(atomElement);\n wrapper.appendChild(tailTextNode);\n\n var wrappedElement = wrapElement(wrapper, atom.openedMarkups);\n attachElementToParent(wrappedElement, element, previousRenderNode);\n\n return {\n markupElement: wrappedElement,\n wrapper: wrapper,\n atomElement: atomElement,\n headTextNode: headTextNode,\n tailTextNode: tailTextNode\n };\n }\n\n function getNextMarkerElement(renderNode) {\n var element = renderNode.element.parentNode;\n var marker = renderNode.postNode;\n var closedCount = marker.closedMarkups.length;\n\n while (closedCount--) {\n element = element.parentNode;\n }\n return element;\n }\n\n /**\n * Render the marker\n * @param {Marker} marker the marker to render\n * @param {DOMNode} element the element to attach the rendered marker to\n * @param {RenderNode} [previousRenderNode] The render node before this one, which\n * affects the determination of where to insert this rendered marker.\n * @return {Object} With properties `element` and `markupElement`.\n * The element (textNode) that has the text for\n * this marker, and the outermost rendered element. If the marker has no\n * markups, element and markupElement will be the same textNode\n * @private\n */\n function renderMarker(marker, parentElement, previousRenderNode) {\n var text = renderHTMLText(marker);\n\n var element = document.createTextNode(text);\n var markupElement = wrapElement(element, marker.openedMarkups);\n attachElementToParent(markupElement, parentElement, previousRenderNode);\n\n return { element: element, markupElement: markupElement };\n }\n\n // Attach the render node's element to the DOM,\n // replacing the originalElement if it exists\n function attachRenderNodeElementToDOM(renderNode) {\n var originalElement = arguments.length <= 1 || arguments[1] === undefined ? null : arguments[1];\n\n var element = renderNode.element;\n var hasRendered = !!originalElement;\n\n if (hasRendered) {\n var parentElement = renderNode.parent.element;\n parentElement.replaceChild(element, originalElement);\n } else {\n var parentElement = undefined,\n nextSiblingElement = undefined;\n if (renderNode.prev) {\n var previousElement = renderNode.prev.element;\n parentElement = previousElement.parentNode;\n nextSiblingElement = previousElement.nextSibling;\n } else {\n parentElement = renderNode.parent.element;\n nextSiblingElement = parentElement.firstChild;\n }\n parentElement.insertBefore(element, nextSiblingElement);\n }\n }\n\n function removeRenderNodeSectionFromParent(renderNode, section) {\n var parent = renderNode.parent.postNode;\n parent.sections.remove(section);\n }\n\n function removeRenderNodeElementFromParent(renderNode) {\n if (renderNode.element && renderNode.element.parentNode) {\n renderNode.element.parentNode.removeChild(renderNode.element);\n }\n }\n\n function validateCards() {\n var cards = arguments.length <= 0 || arguments[0] === undefined ? [] : arguments[0];\n\n (0, _mobiledocKitUtilsArrayUtils.forEach)(cards, function (card) {\n (0, _mobiledocKitUtilsAssert['default'])('Card \"' + card.name + '\" must define type \"dom\", has: \"' + card.type + '\"', card.type === 'dom');\n (0, _mobiledocKitUtilsAssert['default'])('Card \"' + card.name + '\" must define `render` method', !!card.render);\n });\n return cards;\n }\n\n function validateAtoms() {\n var atoms = arguments.length <= 0 || arguments[0] === undefined ? [] : arguments[0];\n\n (0, _mobiledocKitUtilsArrayUtils.forEach)(atoms, function (atom) {\n (0, _mobiledocKitUtilsAssert['default'])('Atom \"' + atom.name + '\" must define type \"dom\", has: \"' + atom.type + '\"', atom.type === 'dom');\n (0, _mobiledocKitUtilsAssert['default'])('Atom \"' + atom.name + '\" must define `render` method', !!atom.render);\n });\n return atoms;\n }\n\n var Visitor = (function () {\n function Visitor(editor, cards, atoms, unknownCardHandler, unknownAtomHandler, options) {\n _classCallCheck(this, Visitor);\n\n this.editor = editor;\n this.cards = validateCards(cards);\n this.atoms = validateAtoms(atoms);\n this.unknownCardHandler = unknownCardHandler;\n this.unknownAtomHandler = unknownAtomHandler;\n this.options = options;\n }\n\n _createClass(Visitor, [{\n key: '_findCard',\n value: function _findCard(cardName) {\n var card = (0, _mobiledocKitUtilsArrayUtils.detect)(this.cards, function (card) {\n return card.name === cardName;\n });\n return card || this._createUnknownCard(cardName);\n }\n }, {\n key: '_createUnknownCard',\n value: function _createUnknownCard(cardName) {\n (0, _mobiledocKitUtilsAssert['default'])('Unknown card \"' + cardName + '\" found, but no unknownCardHandler is defined', !!this.unknownCardHandler);\n\n return {\n name: cardName,\n type: 'dom',\n render: this.unknownCardHandler,\n edit: this.unknownCardHandler\n };\n }\n }, {\n key: '_findAtom',\n value: function _findAtom(atomName) {\n var atom = (0, _mobiledocKitUtilsArrayUtils.detect)(this.atoms, function (atom) {\n return atom.name === atomName;\n });\n return atom || this._createUnknownAtom(atomName);\n }\n }, {\n key: '_createUnknownAtom',\n value: function _createUnknownAtom(atomName) {\n (0, _mobiledocKitUtilsAssert['default'])('Unknown atom \"' + atomName + '\" found, but no unknownAtomHandler is defined', !!this.unknownAtomHandler);\n\n return {\n name: atomName,\n type: 'dom',\n render: this.unknownAtomHandler\n };\n }\n }, {\n key: _mobiledocKitModelsTypes.POST_TYPE,\n value: function value(renderNode, post, visit) {\n if (!renderNode.element) {\n renderNode.element = document.createElement('div');\n }\n (0, _mobiledocKitUtilsDomUtils.addClassName)(renderNode.element, EDITOR_ELEMENT_CLASS_NAME);\n if (post.hasContent) {\n (0, _mobiledocKitUtilsDomUtils.removeClassName)(renderNode.element, EDITOR_HAS_NO_CONTENT_CLASS_NAME);\n } else {\n (0, _mobiledocKitUtilsDomUtils.addClassName)(renderNode.element, EDITOR_HAS_NO_CONTENT_CLASS_NAME);\n }\n visit(renderNode, post.sections);\n }\n }, {\n key: _mobiledocKitModelsTypes.MARKUP_SECTION_TYPE,\n value: function value(renderNode, section, visit) {\n var originalElement = renderNode.element;\n\n // Always rerender the section -- its tag name or attributes may have changed.\n // TODO make this smarter, only rerendering and replacing the element when necessary\n renderNode.element = renderMarkupSection(section);\n renderNode.cursorElement = null;\n attachRenderNodeElementToDOM(renderNode, originalElement);\n\n if (section.isBlank) {\n var cursorPlaceholder = renderCursorPlaceholder();\n renderNode.element.appendChild(cursorPlaceholder);\n renderNode.cursorElement = cursorPlaceholder;\n } else {\n var visitAll = true;\n visit(renderNode, section.markers, visitAll);\n }\n }\n }, {\n key: _mobiledocKitModelsTypes.LIST_SECTION_TYPE,\n value: function value(renderNode, section, visit) {\n var originalElement = renderNode.element;\n\n renderNode.element = renderListSection(section);\n attachRenderNodeElementToDOM(renderNode, originalElement);\n\n var visitAll = true;\n visit(renderNode, section.items, visitAll);\n }\n }, {\n key: _mobiledocKitModelsTypes.LIST_ITEM_TYPE,\n value: function value(renderNode, item, visit) {\n // FIXME do we need to do anything special for rerenders?\n renderNode.element = renderListItem();\n renderNode.cursorElement = null;\n attachRenderNodeElementToDOM(renderNode, null);\n\n if (item.isBlank) {\n var cursorPlaceholder = renderCursorPlaceholder();\n renderNode.element.appendChild(cursorPlaceholder);\n renderNode.cursorElement = cursorPlaceholder;\n } else {\n var visitAll = true;\n visit(renderNode, item.markers, visitAll);\n }\n }\n }, {\n key: _mobiledocKitModelsTypes.MARKER_TYPE,\n value: function value(renderNode, marker) {\n var parentElement = undefined;\n\n if (renderNode.prev) {\n parentElement = getNextMarkerElement(renderNode.prev);\n } else {\n parentElement = renderNode.parent.element;\n }\n\n var _renderMarker = renderMarker(marker, parentElement, renderNode.prev);\n\n var element = _renderMarker.element;\n var markupElement = _renderMarker.markupElement;\n\n renderNode.element = element;\n renderNode.markupElement = markupElement;\n }\n }, {\n key: _mobiledocKitModelsTypes.IMAGE_SECTION_TYPE,\n value: function value(renderNode, section) {\n if (renderNode.element) {\n if (renderNode.element.src !== section.src) {\n renderNode.element.src = section.src;\n }\n } else {\n var element = document.createElement('img');\n element.src = section.src;\n if (renderNode.prev) {\n var previousElement = renderNode.prev.element;\n var nextElement = previousElement.nextSibling;\n if (nextElement) {\n nextElement.parentNode.insertBefore(element, nextElement);\n }\n }\n if (!element.parentNode) {\n renderNode.parent.element.appendChild(element);\n }\n renderNode.element = element;\n }\n }\n }, {\n key: _mobiledocKitModelsTypes.CARD_TYPE,\n value: function value(renderNode, section) {\n var originalElement = renderNode.element;\n var editor = this.editor;\n var options = this.options;\n\n var card = this._findCard(section.name);\n\n var _renderCard = renderCard();\n\n var wrapper = _renderCard.wrapper;\n var cardElement = _renderCard.cardElement;\n\n renderNode.element = wrapper;\n attachRenderNodeElementToDOM(renderNode, originalElement);\n\n var cardNode = new _mobiledocKitModelsCardNode['default'](editor, card, section, cardElement, options);\n renderNode.cardNode = cardNode;\n\n var initialMode = section._initialMode;\n cardNode[initialMode]();\n }\n }, {\n key: _mobiledocKitModelsTypes.ATOM_TYPE,\n value: function value(renderNode, atomModel) {\n var parentElement = undefined;\n\n if (renderNode.prev) {\n parentElement = getNextMarkerElement(renderNode.prev);\n } else {\n parentElement = renderNode.parent.element;\n }\n\n var editor = this.editor;\n var options = this.options;\n\n var _renderAtom = renderAtom(atomModel, parentElement, renderNode.prev);\n\n var wrapper = _renderAtom.wrapper;\n var markupElement = _renderAtom.markupElement;\n var atomElement = _renderAtom.atomElement;\n var headTextNode = _renderAtom.headTextNode;\n var tailTextNode = _renderAtom.tailTextNode;\n\n var atom = this._findAtom(atomModel.name);\n\n var atomNode = renderNode.atomNode;\n if (!atomNode) {\n // create new AtomNode\n atomNode = new _mobiledocKitModelsAtomNode['default'](editor, atom, atomModel, atomElement, options);\n } else {\n // retarget atomNode to new atom element\n atomNode.element = atomElement;\n }\n\n atomNode.render();\n\n renderNode.atomNode = atomNode;\n renderNode.element = wrapper;\n renderNode.headTextNode = headTextNode;\n renderNode.tailTextNode = tailTextNode;\n renderNode.markupElement = markupElement;\n }\n }]);\n\n return Visitor;\n })();\n\n var destroyHooks = (_destroyHooks = {}, _defineProperty(_destroyHooks, _mobiledocKitModelsTypes.POST_TYPE, function () /*renderNode, post*/{\n (0, _mobiledocKitUtilsAssert['default'])('post destruction is not supported by the renderer', false);\n }), _defineProperty(_destroyHooks, _mobiledocKitModelsTypes.MARKUP_SECTION_TYPE, function (renderNode, section) {\n removeRenderNodeSectionFromParent(renderNode, section);\n removeRenderNodeElementFromParent(renderNode);\n }), _defineProperty(_destroyHooks, _mobiledocKitModelsTypes.LIST_SECTION_TYPE, function (renderNode, section) {\n removeRenderNodeSectionFromParent(renderNode, section);\n removeRenderNodeElementFromParent(renderNode);\n }), _defineProperty(_destroyHooks, _mobiledocKitModelsTypes.LIST_ITEM_TYPE, function (renderNode, li) {\n removeRenderNodeSectionFromParent(renderNode, li);\n removeRenderNodeElementFromParent(renderNode);\n }), _defineProperty(_destroyHooks, _mobiledocKitModelsTypes.MARKER_TYPE, function (renderNode, marker) {\n // FIXME before we render marker, should delete previous renderNode's element\n // and up until the next marker element\n\n // If an atom throws during render we may end up later destroying a renderNode\n // that has not rendered yet, so exit early here if so.\n if (!renderNode.isRendered) {\n return;\n }\n var markupElement = renderNode.markupElement;\n\n if (marker.section) {\n marker.section.markers.remove(marker);\n }\n\n if (markupElement.parentNode) {\n // if no parentNode, the browser already removed this element\n markupElement.parentNode.removeChild(markupElement);\n }\n }), _defineProperty(_destroyHooks, _mobiledocKitModelsTypes.IMAGE_SECTION_TYPE, function (renderNode, section) {\n removeRenderNodeSectionFromParent(renderNode, section);\n removeRenderNodeElementFromParent(renderNode);\n }), _defineProperty(_destroyHooks, _mobiledocKitModelsTypes.CARD_TYPE, function (renderNode, section) {\n if (renderNode.cardNode) {\n renderNode.cardNode.teardown();\n }\n removeRenderNodeSectionFromParent(renderNode, section);\n removeRenderNodeElementFromParent(renderNode);\n }), _defineProperty(_destroyHooks, _mobiledocKitModelsTypes.ATOM_TYPE, function (renderNode, atom) {\n if (renderNode.atomNode) {\n renderNode.atomNode.teardown();\n }\n\n // an atom is a kind of marker so just call its destroy hook vs copying here\n destroyHooks[_mobiledocKitModelsTypes.MARKER_TYPE](renderNode, atom);\n }), _destroyHooks);\n\n // removes children from parentNode (a RenderNode) that are scheduled for removal\n function removeDestroyedChildren(parentNode) {\n var forceRemoval = arguments.length <= 1 || arguments[1] === undefined ? false : arguments[1];\n\n var child = parentNode.childNodes.head;\n var nextChild = undefined,\n method = undefined;\n while (child) {\n nextChild = child.next;\n if (child.isRemoved || forceRemoval) {\n removeDestroyedChildren(child, true);\n method = child.postNode.type;\n (0, _mobiledocKitUtilsAssert['default'])('editor-dom cannot destroy \"' + method + '\"', !!destroyHooks[method]);\n destroyHooks[method](child, child.postNode);\n parentNode.childNodes.remove(child);\n }\n child = nextChild;\n }\n }\n\n // Find an existing render node for the given postNode, or\n // create one, insert it into the tree, and return it\n function lookupNode(renderTree, parentNode, postNode, previousNode) {\n if (postNode.renderNode) {\n return postNode.renderNode;\n } else {\n var renderNode = renderTree.buildRenderNode(postNode);\n parentNode.childNodes.insertAfter(renderNode, previousNode);\n return renderNode;\n }\n }\n\n var Renderer = (function () {\n function Renderer(editor, cards, atoms, unknownCardHandler, unknownAtomHandler, options) {\n _classCallCheck(this, Renderer);\n\n this.editor = editor;\n this.visitor = new Visitor(editor, cards, atoms, unknownCardHandler, unknownAtomHandler, options);\n this.nodes = [];\n this.hasRendered = false;\n }\n\n _createClass(Renderer, [{\n key: 'destroy',\n value: function destroy() {\n if (!this.hasRendered) {\n return;\n }\n var renderNode = this.renderTree.rootNode;\n var force = true;\n removeDestroyedChildren(renderNode, force);\n }\n }, {\n key: 'visit',\n value: function visit(renderTree, parentNode, postNodes) {\n var _this = this;\n\n var visitAll = arguments.length <= 3 || arguments[3] === undefined ? false : arguments[3];\n\n var previousNode = undefined;\n postNodes.forEach(function (postNode) {\n var node = lookupNode(renderTree, parentNode, postNode, previousNode);\n if (node.isDirty || visitAll) {\n _this.nodes.push(node);\n }\n previousNode = node;\n });\n }\n }, {\n key: 'render',\n value: function render(renderTree) {\n var _this2 = this;\n\n this.hasRendered = true;\n this.renderTree = renderTree;\n var renderNode = renderTree.rootNode;\n var method = undefined,\n postNode = undefined;\n\n while (renderNode) {\n removeDestroyedChildren(renderNode);\n postNode = renderNode.postNode;\n\n method = postNode.type;\n (0, _mobiledocKitUtilsAssert['default'])('EditorDom visitor cannot handle type ' + method, !!this.visitor[method]);\n // jshint -W083\n this.visitor[method](renderNode, postNode, function () {\n for (var _len = arguments.length, args = Array(_len), _key = 0; _key < _len; _key++) {\n args[_key] = arguments[_key];\n }\n\n return _this2.visit.apply(_this2, [renderTree].concat(args));\n });\n // jshint +W083\n renderNode.markClean();\n renderNode = this.nodes.shift();\n }\n }\n }]);\n\n return Renderer;\n })();\n\n exports['default'] = Renderer;\n});","define('mobiledoc-kit/renderers/mobiledoc/0-2', ['exports', 'mobiledoc-kit/utils/compiler', 'mobiledoc-kit/utils/array-utils', 'mobiledoc-kit/models/types'], function (exports, _mobiledocKitUtilsCompiler, _mobiledocKitUtilsArrayUtils, _mobiledocKitModelsTypes) {\n 'use strict';\n\n var _visitor;\n\n function _defineProperty(obj, key, value) { if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; }\n\n var MOBILEDOC_VERSION = '0.2.0';\n exports.MOBILEDOC_VERSION = MOBILEDOC_VERSION;\n var MOBILEDOC_MARKUP_SECTION_TYPE = 1;\n exports.MOBILEDOC_MARKUP_SECTION_TYPE = MOBILEDOC_MARKUP_SECTION_TYPE;\n var MOBILEDOC_IMAGE_SECTION_TYPE = 2;\n exports.MOBILEDOC_IMAGE_SECTION_TYPE = MOBILEDOC_IMAGE_SECTION_TYPE;\n var MOBILEDOC_LIST_SECTION_TYPE = 3;\n exports.MOBILEDOC_LIST_SECTION_TYPE = MOBILEDOC_LIST_SECTION_TYPE;\n var MOBILEDOC_CARD_SECTION_TYPE = 10;\n\n exports.MOBILEDOC_CARD_SECTION_TYPE = MOBILEDOC_CARD_SECTION_TYPE;\n var visitor = (_visitor = {}, _defineProperty(_visitor, _mobiledocKitModelsTypes.POST_TYPE, function (node, opcodes) {\n opcodes.push(['openPost']);\n (0, _mobiledocKitUtilsCompiler.visitArray)(visitor, node.sections, opcodes);\n }), _defineProperty(_visitor, _mobiledocKitModelsTypes.MARKUP_SECTION_TYPE, function (node, opcodes) {\n opcodes.push(['openMarkupSection', node.tagName]);\n (0, _mobiledocKitUtilsCompiler.visitArray)(visitor, node.markers, opcodes);\n }), _defineProperty(_visitor, _mobiledocKitModelsTypes.LIST_SECTION_TYPE, function (node, opcodes) {\n opcodes.push(['openListSection', node.tagName]);\n (0, _mobiledocKitUtilsCompiler.visitArray)(visitor, node.items, opcodes);\n }), _defineProperty(_visitor, _mobiledocKitModelsTypes.LIST_ITEM_TYPE, function (node, opcodes) {\n opcodes.push(['openListItem']);\n (0, _mobiledocKitUtilsCompiler.visitArray)(visitor, node.markers, opcodes);\n }), _defineProperty(_visitor, _mobiledocKitModelsTypes.IMAGE_SECTION_TYPE, function (node, opcodes) {\n opcodes.push(['openImageSection', node.src]);\n }), _defineProperty(_visitor, _mobiledocKitModelsTypes.CARD_TYPE, function (node, opcodes) {\n opcodes.push(['openCardSection', node.name, node.payload]);\n }), _defineProperty(_visitor, _mobiledocKitModelsTypes.MARKER_TYPE, function (node, opcodes) {\n opcodes.push(['openMarker', node.closedMarkups.length, node.value]);\n (0, _mobiledocKitUtilsCompiler.visitArray)(visitor, node.openedMarkups, opcodes);\n }), _defineProperty(_visitor, _mobiledocKitModelsTypes.MARKUP_TYPE, function (node, opcodes) {\n opcodes.push(['openMarkup', node.tagName, (0, _mobiledocKitUtilsArrayUtils.objectToSortedKVArray)(node.attributes)]);\n }), _visitor);\n\n var postOpcodeCompiler = {\n openMarker: function openMarker(closeCount, value) {\n this.markupMarkerIds = [];\n this.markers.push([this.markupMarkerIds, closeCount, value || '']);\n },\n openMarkupSection: function openMarkupSection(tagName) {\n this.markers = [];\n this.sections.push([MOBILEDOC_MARKUP_SECTION_TYPE, tagName, this.markers]);\n },\n openListSection: function openListSection(tagName) {\n this.items = [];\n this.sections.push([MOBILEDOC_LIST_SECTION_TYPE, tagName, this.items]);\n },\n openListItem: function openListItem() {\n this.markers = [];\n this.items.push(this.markers);\n },\n openImageSection: function openImageSection(url) {\n this.sections.push([MOBILEDOC_IMAGE_SECTION_TYPE, url]);\n },\n openCardSection: function openCardSection(name, payload) {\n this.sections.push([MOBILEDOC_CARD_SECTION_TYPE, name, payload]);\n },\n openPost: function openPost() {\n this.markerTypes = [];\n this.sections = [];\n this.result = {\n version: MOBILEDOC_VERSION,\n sections: [this.markerTypes, this.sections]\n };\n },\n openMarkup: function openMarkup(tagName, attributes) {\n var index = this._findOrAddMarkerTypeIndex(tagName, attributes);\n this.markupMarkerIds.push(index);\n },\n _findOrAddMarkerTypeIndex: function _findOrAddMarkerTypeIndex(tagName, attributesArray) {\n if (!this._markerTypeCache) {\n this._markerTypeCache = {};\n }\n var key = tagName + '-' + attributesArray.join('-');\n\n var index = this._markerTypeCache[key];\n if (index === undefined) {\n var markerType = [tagName];\n if (attributesArray.length) {\n markerType.push(attributesArray);\n }\n this.markerTypes.push(markerType);\n\n index = this.markerTypes.length - 1;\n this._markerTypeCache[key] = index;\n }\n\n return index;\n }\n };\n\n /**\n * Render from post -> mobiledoc\n */\n exports['default'] = {\n /**\n * @param {Post}\n * @return {Mobiledoc}\n */\n render: function render(post) {\n var opcodes = [];\n (0, _mobiledocKitUtilsCompiler.visit)(visitor, post, opcodes);\n var compiler = Object.create(postOpcodeCompiler);\n (0, _mobiledocKitUtilsCompiler.compile)(compiler, opcodes);\n return compiler.result;\n }\n };\n});","define('mobiledoc-kit/renderers/mobiledoc/0-3', ['exports', 'mobiledoc-kit/utils/compiler', 'mobiledoc-kit/utils/array-utils', 'mobiledoc-kit/models/types'], function (exports, _mobiledocKitUtilsCompiler, _mobiledocKitUtilsArrayUtils, _mobiledocKitModelsTypes) {\n 'use strict';\n\n var _visitor;\n\n function _defineProperty(obj, key, value) { if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; }\n\n var MOBILEDOC_VERSION = '0.3.0';\n exports.MOBILEDOC_VERSION = MOBILEDOC_VERSION;\n var MOBILEDOC_MARKUP_SECTION_TYPE = 1;\n exports.MOBILEDOC_MARKUP_SECTION_TYPE = MOBILEDOC_MARKUP_SECTION_TYPE;\n var MOBILEDOC_IMAGE_SECTION_TYPE = 2;\n exports.MOBILEDOC_IMAGE_SECTION_TYPE = MOBILEDOC_IMAGE_SECTION_TYPE;\n var MOBILEDOC_LIST_SECTION_TYPE = 3;\n exports.MOBILEDOC_LIST_SECTION_TYPE = MOBILEDOC_LIST_SECTION_TYPE;\n var MOBILEDOC_CARD_SECTION_TYPE = 10;\n\n exports.MOBILEDOC_CARD_SECTION_TYPE = MOBILEDOC_CARD_SECTION_TYPE;\n var MOBILEDOC_MARKUP_MARKER_TYPE = 0;\n exports.MOBILEDOC_MARKUP_MARKER_TYPE = MOBILEDOC_MARKUP_MARKER_TYPE;\n var MOBILEDOC_ATOM_MARKER_TYPE = 1;\n\n exports.MOBILEDOC_ATOM_MARKER_TYPE = MOBILEDOC_ATOM_MARKER_TYPE;\n var visitor = (_visitor = {}, _defineProperty(_visitor, _mobiledocKitModelsTypes.POST_TYPE, function (node, opcodes) {\n opcodes.push(['openPost']);\n (0, _mobiledocKitUtilsCompiler.visitArray)(visitor, node.sections, opcodes);\n }), _defineProperty(_visitor, _mobiledocKitModelsTypes.MARKUP_SECTION_TYPE, function (node, opcodes) {\n opcodes.push(['openMarkupSection', node.tagName]);\n (0, _mobiledocKitUtilsCompiler.visitArray)(visitor, node.markers, opcodes);\n }), _defineProperty(_visitor, _mobiledocKitModelsTypes.LIST_SECTION_TYPE, function (node, opcodes) {\n opcodes.push(['openListSection', node.tagName]);\n (0, _mobiledocKitUtilsCompiler.visitArray)(visitor, node.items, opcodes);\n }), _defineProperty(_visitor, _mobiledocKitModelsTypes.LIST_ITEM_TYPE, function (node, opcodes) {\n opcodes.push(['openListItem']);\n (0, _mobiledocKitUtilsCompiler.visitArray)(visitor, node.markers, opcodes);\n }), _defineProperty(_visitor, _mobiledocKitModelsTypes.IMAGE_SECTION_TYPE, function (node, opcodes) {\n opcodes.push(['openImageSection', node.src]);\n }), _defineProperty(_visitor, _mobiledocKitModelsTypes.CARD_TYPE, function (node, opcodes) {\n opcodes.push(['openCardSection', node.name, node.payload]);\n }), _defineProperty(_visitor, _mobiledocKitModelsTypes.MARKER_TYPE, function (node, opcodes) {\n opcodes.push(['openMarker', node.closedMarkups.length, node.value]);\n (0, _mobiledocKitUtilsCompiler.visitArray)(visitor, node.openedMarkups, opcodes);\n }), _defineProperty(_visitor, _mobiledocKitModelsTypes.MARKUP_TYPE, function (node, opcodes) {\n opcodes.push(['openMarkup', node.tagName, (0, _mobiledocKitUtilsArrayUtils.objectToSortedKVArray)(node.attributes)]);\n }), _defineProperty(_visitor, _mobiledocKitModelsTypes.ATOM_TYPE, function (node, opcodes) {\n opcodes.push(['openAtom', node.closedMarkups.length, node.name, node.value, node.payload]);\n (0, _mobiledocKitUtilsCompiler.visitArray)(visitor, node.openedMarkups, opcodes);\n }), _visitor);\n\n var postOpcodeCompiler = {\n openMarker: function openMarker(closeCount, value) {\n this.markupMarkerIds = [];\n this.markers.push([MOBILEDOC_MARKUP_MARKER_TYPE, this.markupMarkerIds, closeCount, value || '']);\n },\n openMarkupSection: function openMarkupSection(tagName) {\n this.markers = [];\n this.sections.push([MOBILEDOC_MARKUP_SECTION_TYPE, tagName, this.markers]);\n },\n openListSection: function openListSection(tagName) {\n this.items = [];\n this.sections.push([MOBILEDOC_LIST_SECTION_TYPE, tagName, this.items]);\n },\n openListItem: function openListItem() {\n this.markers = [];\n this.items.push(this.markers);\n },\n openImageSection: function openImageSection(url) {\n this.sections.push([MOBILEDOC_IMAGE_SECTION_TYPE, url]);\n },\n openCardSection: function openCardSection(name, payload) {\n var index = this._addCardTypeIndex(name, payload);\n this.sections.push([MOBILEDOC_CARD_SECTION_TYPE, index]);\n },\n openAtom: function openAtom(closeCount, name, value, payload) {\n var index = this._addAtomTypeIndex(name, value, payload);\n this.markupMarkerIds = [];\n this.markers.push([MOBILEDOC_ATOM_MARKER_TYPE, this.markupMarkerIds, closeCount, index]);\n },\n openPost: function openPost() {\n this.atomTypes = [];\n this.cardTypes = [];\n this.markerTypes = [];\n this.sections = [];\n this.result = {\n version: MOBILEDOC_VERSION,\n atoms: this.atomTypes,\n cards: this.cardTypes,\n markups: this.markerTypes,\n sections: this.sections\n };\n },\n openMarkup: function openMarkup(tagName, attributes) {\n var index = this._findOrAddMarkerTypeIndex(tagName, attributes);\n this.markupMarkerIds.push(index);\n },\n _addCardTypeIndex: function _addCardTypeIndex(cardName, payload) {\n var cardType = [cardName, payload];\n this.cardTypes.push(cardType);\n return this.cardTypes.length - 1;\n },\n _addAtomTypeIndex: function _addAtomTypeIndex(atomName, atomValue, payload) {\n var atomType = [atomName, atomValue, payload];\n this.atomTypes.push(atomType);\n return this.atomTypes.length - 1;\n },\n _findOrAddMarkerTypeIndex: function _findOrAddMarkerTypeIndex(tagName, attributesArray) {\n if (!this._markerTypeCache) {\n this._markerTypeCache = {};\n }\n var key = tagName + '-' + attributesArray.join('-');\n\n var index = this._markerTypeCache[key];\n if (index === undefined) {\n var markerType = [tagName];\n if (attributesArray.length) {\n markerType.push(attributesArray);\n }\n this.markerTypes.push(markerType);\n\n index = this.markerTypes.length - 1;\n this._markerTypeCache[key] = index;\n }\n\n return index;\n }\n };\n\n /**\n * Render from post -> mobiledoc\n */\n exports['default'] = {\n /**\n * @param {Post}\n * @return {Mobiledoc}\n */\n render: function render(post) {\n var opcodes = [];\n (0, _mobiledocKitUtilsCompiler.visit)(visitor, post, opcodes);\n var compiler = Object.create(postOpcodeCompiler);\n (0, _mobiledocKitUtilsCompiler.compile)(compiler, opcodes);\n return compiler.result;\n }\n };\n});","define('mobiledoc-kit/renderers/mobiledoc', ['exports', 'mobiledoc-kit/renderers/mobiledoc/0-2', 'mobiledoc-kit/renderers/mobiledoc/0-3', 'mobiledoc-kit/utils/assert'], function (exports, _mobiledocKitRenderersMobiledoc02, _mobiledocKitRenderersMobiledoc03, _mobiledocKitUtilsAssert) {\n 'use strict';\n\n var MOBILEDOC_VERSION = _mobiledocKitRenderersMobiledoc03.MOBILEDOC_VERSION;\n\n exports.MOBILEDOC_VERSION = MOBILEDOC_VERSION;\n exports['default'] = {\n render: function render(post, version) {\n switch (version) {\n case _mobiledocKitRenderersMobiledoc02.MOBILEDOC_VERSION:\n return _mobiledocKitRenderersMobiledoc02['default'].render(post);\n case undefined:\n case null:\n case _mobiledocKitRenderersMobiledoc03.MOBILEDOC_VERSION:\n return _mobiledocKitRenderersMobiledoc03['default'].render(post);\n default:\n (0, _mobiledocKitUtilsAssert['default'])('Unknown version of mobiledoc renderer requested: ' + version, false);\n }\n }\n };\n});","define(\"mobiledoc-kit/utils/array-utils\", [\"exports\"], function (exports) {\n \"use strict\";\n\n function detect(enumerable, callback) {\n if (enumerable.detect) {\n return enumerable.detect(callback);\n } else {\n for (var i = 0; i < enumerable.length; i++) {\n if (callback(enumerable[i])) {\n return enumerable[i];\n }\n }\n }\n }\n\n function any(enumerable, callback) {\n if (enumerable.any) {\n return enumerable.any(callback);\n }\n\n for (var i = 0; i < enumerable.length; i++) {\n if (callback(enumerable[i])) {\n return true;\n }\n }\n\n return false;\n }\n\n function every(enumerable, callback) {\n if (enumerable.every) {\n return enumerable.every(callback);\n }\n\n for (var i = 0; i < enumerable.length; i++) {\n if (!callback(enumerable[i])) {\n return false;\n }\n }\n return true;\n }\n\n function toArray(arrayLike) {\n return Array.prototype.slice.call(arrayLike);\n }\n\n /**\n * Useful for array-like things that aren't\n * actually arrays, like NodeList\n * @private\n */\n function forEach(enumerable, callback) {\n if (enumerable.forEach) {\n enumerable.forEach(callback);\n } else {\n for (var i = 0; i < enumerable.length; i++) {\n callback(enumerable[i], i);\n }\n }\n }\n\n function filter(enumerable, conditionFn) {\n var filtered = [];\n forEach(enumerable, function (i) {\n if (conditionFn(i)) {\n filtered.push(i);\n }\n });\n return filtered;\n }\n\n /**\n * @return {Integer} the number of items that are the same, starting from the 0th index, in a and b\n * @private\n */\n function commonItemLength(listA, listB) {\n var offset = 0;\n while (offset < listA.length && offset < listB.length) {\n if (listA[offset] !== listB[offset]) {\n break;\n }\n offset++;\n }\n return offset;\n }\n\n /**\n * @return {Array} the items that are the same, starting from the 0th index, in a and b\n * @private\n */\n function commonItems(listA, listB) {\n var offset = 0;\n while (offset < listA.length && offset < listB.length) {\n if (listA[offset] !== listB[offset]) {\n break;\n }\n offset++;\n }\n return listA.slice(0, offset);\n }\n\n // return new array without falsy items like ruby's `compact`\n function compact(enumerable) {\n return filter(enumerable, function (i) {\n return !!i;\n });\n }\n\n function reduce(enumerable, callback, initialValue) {\n var previousValue = initialValue;\n forEach(enumerable, function (val, index) {\n previousValue = callback(previousValue, val, index);\n });\n return previousValue;\n }\n\n /**\n * @param {Array} array of key1,value1,key2,value2,...\n * @return {Object} {key1:value1, key2:value2, ...}\n * @private\n */\n function kvArrayToObject(array) {\n var obj = {};\n for (var i = 0; i < array.length; i += 2) {\n var key = array[i];\n var value = array[i + 1];\n\n obj[key] = value;\n }\n return obj;\n }\n\n function objectToSortedKVArray(obj) {\n var keys = Object.keys(obj).sort();\n var result = [];\n keys.forEach(function (k) {\n result.push(k);\n result.push(obj[k]);\n });\n return result;\n }\n\n // check shallow equality of two non-nested arrays\n function isArrayEqual(arr1, arr2) {\n var l1 = arr1.length,\n l2 = arr2.length;\n if (l1 !== l2) {\n return false;\n }\n\n for (var i = 0; i < l1; i++) {\n if (arr1[i] !== arr2[i]) {\n return false;\n }\n }\n return true;\n }\n\n // return an object with only the valid keys\n function filterObject(object) {\n var validKeys = arguments.length <= 1 || arguments[1] === undefined ? [] : arguments[1];\n\n var result = {};\n forEach(filter(Object.keys(object), function (key) {\n return validKeys.indexOf(key) !== -1;\n }), function (key) {\n return result[key] = object[key];\n });\n return result;\n }\n\n function contains(array, item) {\n return array.indexOf(item) !== -1;\n }\n\n function values(object) {\n return Object.keys(object).map(function (key) {\n return object[key];\n });\n }\n\n exports.detect = detect;\n exports.forEach = forEach;\n exports.any = any;\n exports.every = every;\n exports.filter = filter;\n exports.commonItemLength = commonItemLength;\n exports.commonItems = commonItems;\n exports.compact = compact;\n exports.reduce = reduce;\n exports.objectToSortedKVArray = objectToSortedKVArray;\n exports.kvArrayToObject = kvArrayToObject;\n exports.isArrayEqual = isArrayEqual;\n exports.toArray = toArray;\n exports.filterObject = filterObject;\n exports.contains = contains;\n exports.values = values;\n});","define('mobiledoc-kit/utils/assert', ['exports', 'mobiledoc-kit/utils/mobiledoc-error'], function (exports, _mobiledocKitUtilsMobiledocError) {\n 'use strict';\n\n exports['default'] = function (message, conditional) {\n if (!conditional) {\n throw new _mobiledocKitUtilsMobiledocError['default'](message);\n }\n };\n});","define('mobiledoc-kit/utils/browser', ['exports'], function (exports) {\n 'use strict';\n\n exports['default'] = {\n isMac: function isMac() {\n return typeof window !== 'undefined' && window.navigator && /Mac/.test(window.navigator.platform);\n },\n isWin: function isWin() {\n return typeof window !== 'undefined' && window.navigator && /Win/.test(window.navigator.platform);\n }\n };\n});","define('mobiledoc-kit/utils/characters', ['exports'], function (exports) {\n 'use strict';\n\n var TAB = '\\t';\n exports.TAB = TAB;\n var ENTER = '\\n';\n exports.ENTER = ENTER;\n var SPACE = ' ';\n exports.SPACE = SPACE;\n});","define('mobiledoc-kit/utils/compiler', ['exports', 'mobiledoc-kit/utils/array-utils', 'mobiledoc-kit/utils/assert'], function (exports, _mobiledocKitUtilsArrayUtils, _mobiledocKitUtilsAssert) {\n 'use strict';\n\n exports.visit = visit;\n exports.compile = compile;\n exports.visitArray = visitArray;\n\n function _toArray(arr) { return Array.isArray(arr) ? arr : Array.from(arr); }\n\n function visit(visitor, node, opcodes) {\n var method = node.type;\n (0, _mobiledocKitUtilsAssert['default'])('Cannot visit unknown type ' + method, !!visitor[method]);\n visitor[method](node, opcodes);\n }\n\n function compile(compiler, opcodes) {\n for (var i = 0, l = opcodes.length; i < l; i++) {\n var _opcodes$i = _toArray(opcodes[i]);\n\n var method = _opcodes$i[0];\n\n var params = _opcodes$i.slice(1);\n\n var _length = params.length;\n if (_length === 0) {\n compiler[method].call(compiler);\n } else if (_length === 1) {\n compiler[method].call(compiler, params[0]);\n } else if (_length === 2) {\n compiler[method].call(compiler, params[0], params[1]);\n } else {\n compiler[method].apply(compiler, params);\n }\n }\n }\n\n function visitArray(visitor, nodes, opcodes) {\n if (!nodes || nodes.length === 0) {\n return;\n }\n (0, _mobiledocKitUtilsArrayUtils.forEach)(nodes, function (node) {\n visit(visitor, node, opcodes);\n });\n }\n});","define(\"mobiledoc-kit/utils/copy\", [\"exports\"], function (exports) {\n \"use strict\";\n\n function shallowCopyObject(object) {\n var copy = {};\n Object.keys(object).forEach(function (key) {\n copy[key] = object[key];\n });\n return copy;\n }\n\n exports.shallowCopyObject = shallowCopyObject;\n});","define('mobiledoc-kit/utils/cursor', ['exports', 'mobiledoc-kit/utils/selection-utils', 'mobiledoc-kit/utils/dom-utils', 'mobiledoc-kit/utils/cursor/position', 'mobiledoc-kit/utils/cursor/range', 'mobiledoc-kit/utils/key'], function (exports, _mobiledocKitUtilsSelectionUtils, _mobiledocKitUtilsDomUtils, _mobiledocKitUtilsCursorPosition, _mobiledocKitUtilsCursorRange, _mobiledocKitUtilsKey) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n exports.Position = _mobiledocKitUtilsCursorPosition['default'];\n exports.Range = _mobiledocKitUtilsCursorRange['default'];\n\n var Cursor = (function () {\n function Cursor(editor) {\n _classCallCheck(this, Cursor);\n\n this.editor = editor;\n this.renderTree = editor._renderTree;\n this.post = editor.post;\n }\n\n _createClass(Cursor, [{\n key: 'clearSelection',\n value: function clearSelection() {\n (0, _mobiledocKitUtilsSelectionUtils.clearSelection)();\n }\n\n /**\n * @return {Boolean} true when there is either a collapsed cursor in the\n * editor's element or a selection that is contained in the editor's element\n */\n }, {\n key: 'hasCursor',\n value: function hasCursor() {\n return this.editor.hasRendered && (this._hasCollapsedSelection() || this._hasSelection());\n }\n }, {\n key: 'hasSelection',\n value: function hasSelection() {\n return this.editor.hasRendered && this._hasSelection();\n }\n\n /**\n * @return {Boolean} Can the cursor be on this element?\n */\n }, {\n key: 'isAddressable',\n value: function isAddressable(element) {\n var renderTree = this.renderTree;\n\n var renderNode = renderTree.findRenderNodeFromElement(element);\n if (renderNode && renderNode.postNode.isCardSection) {\n var renderedElement = renderNode.element;\n\n // card sections have addressable text nodes containing ‌\n // as their first and last child\n if (element !== renderedElement && element !== renderedElement.firstChild && element !== renderedElement.lastChild) {\n return false;\n }\n }\n\n return !!renderNode;\n }\n\n /*\n * @return {Range} Cursor#Range object\n */\n }, {\n key: '_findNodeForPosition',\n value: function _findNodeForPosition(position) {\n var section = position.section;\n\n var node = undefined,\n offset = undefined;\n if (section.isCardSection) {\n offset = 0;\n if (position.offset === 0) {\n node = section.renderNode.element.firstChild;\n } else {\n node = section.renderNode.element.lastChild;\n }\n } else if (section.isBlank) {\n node = section.renderNode.cursorElement;\n offset = 0;\n } else {\n var marker = position.marker;\n var offsetInMarker = position.offsetInMarker;\n\n if (marker.isAtom) {\n if (offsetInMarker > 0) {\n // FIXME -- if there is a next marker, focus on it?\n offset = 0;\n node = marker.renderNode.tailTextNode;\n } else {\n offset = 0;\n node = marker.renderNode.headTextNode;\n }\n } else {\n node = marker.renderNode.element;\n offset = offsetInMarker;\n }\n }\n\n return { node: node, offset: offset };\n }\n }, {\n key: 'selectRange',\n value: function selectRange(range) {\n if (range.isBlank) {\n this.clearSelection();\n return;\n }\n\n var head = range.head;\n var tail = range.tail;\n var direction = range.direction;\n\n var _findNodeForPosition2 = this._findNodeForPosition(head);\n\n var headNode = _findNodeForPosition2.node;\n var headOffset = _findNodeForPosition2.offset;\n\n var _findNodeForPosition3 = this._findNodeForPosition(tail);\n\n var tailNode = _findNodeForPosition3.node;\n var tailOffset = _findNodeForPosition3.offset;\n\n this._moveToNode(headNode, headOffset, tailNode, tailOffset, direction);\n\n // Firefox sometimes doesn't keep focus in the editor after adding a card\n this.editor._ensureFocus();\n }\n }, {\n key: 'selectedText',\n value: function selectedText() {\n // FIXME remove this\n return this.selection.toString();\n }\n\n /**\n * @param {textNode} node\n * @param {integer} offset\n * @param {textNode} endNode\n * @param {integer} endOffset\n * @param {integer} direction forward or backward, default forward\n * @private\n */\n }, {\n key: '_moveToNode',\n value: function _moveToNode(node, offset, endNode, endOffset) {\n var direction = arguments.length <= 4 || arguments[4] === undefined ? _mobiledocKitUtilsKey.DIRECTION.FORWARD : arguments[4];\n\n this.clearSelection();\n\n if (direction === _mobiledocKitUtilsKey.DIRECTION.BACKWARD) {\n var _ref = [endNode, endOffset, node, offset];\n node = _ref[0];\n offset = _ref[1];\n endNode = _ref[2];\n endOffset = _ref[3];\n }\n\n var range = document.createRange();\n range.setStart(node, offset);\n if (direction === _mobiledocKitUtilsKey.DIRECTION.BACKWARD && !!this.selection.extend) {\n this.selection.addRange(range);\n this.selection.extend(endNode, endOffset);\n } else {\n range.setEnd(endNode, endOffset);\n this.selection.addRange(range);\n }\n }\n }, {\n key: '_hasSelection',\n value: function _hasSelection() {\n var element = this.editor.element;\n var _selectionRange = this._selectionRange;\n\n if (!_selectionRange || _selectionRange.collapsed) {\n return false;\n }\n\n return (0, _mobiledocKitUtilsDomUtils.containsNode)(element, this.selection.anchorNode) && (0, _mobiledocKitUtilsDomUtils.containsNode)(element, this.selection.focusNode);\n }\n }, {\n key: '_hasCollapsedSelection',\n value: function _hasCollapsedSelection() {\n var _selectionRange = this._selectionRange;\n\n if (!_selectionRange) {\n return false;\n }\n\n var element = this.editor.element;\n return (0, _mobiledocKitUtilsDomUtils.containsNode)(element, this.selection.anchorNode);\n }\n }, {\n key: 'offsets',\n get: function get() {\n if (!this.hasCursor()) {\n return _mobiledocKitUtilsCursorRange['default'].blankRange();\n }\n\n var selection = this.selection;\n var renderTree = this.renderTree;\n\n var _comparePosition = (0, _mobiledocKitUtilsSelectionUtils.comparePosition)(selection);\n\n var headNode = _comparePosition.headNode;\n var headOffset = _comparePosition.headOffset;\n var tailNode = _comparePosition.tailNode;\n var tailOffset = _comparePosition.tailOffset;\n var direction = _comparePosition.direction;\n\n var headPosition = _mobiledocKitUtilsCursorPosition['default'].fromNode(renderTree, headNode, headOffset);\n var tailPosition = _mobiledocKitUtilsCursorPosition['default'].fromNode(renderTree, tailNode, tailOffset);\n\n return new _mobiledocKitUtilsCursorRange['default'](headPosition, tailPosition, direction);\n }\n }, {\n key: 'selection',\n get: function get() {\n return window.getSelection();\n }\n }, {\n key: '_selectionRange',\n get: function get() {\n var selection = this.selection;\n\n if (selection.rangeCount === 0) {\n return null;\n }\n return selection.getRangeAt(0);\n }\n }]);\n\n return Cursor;\n })();\n\n exports['default'] = Cursor;\n});","define('mobiledoc-kit/utils/cursor/position', ['exports', 'mobiledoc-kit/utils/dom-utils', 'mobiledoc-kit/utils/assert', 'mobiledoc-kit/models/marker', 'mobiledoc-kit/utils/selection-utils', 'mobiledoc-kit/utils/key', 'mobiledoc-kit/utils/cursor/range'], function (exports, _mobiledocKitUtilsDomUtils, _mobiledocKitUtilsAssert, _mobiledocKitModelsMarker, _mobiledocKitUtilsSelectionUtils, _mobiledocKitUtilsKey, _mobiledocKitUtilsCursorRange) {\n 'use strict';\n\n var _get = function get(_x4, _x5, _x6) { var _again = true; _function: while (_again) { var object = _x4, property = _x5, receiver = _x6; _again = false; if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { _x4 = parent; _x5 = property; _x6 = receiver; _again = true; desc = parent = undefined; continue _function; } } else if ('value' in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } } };\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _inherits(subClass, superClass) { if (typeof superClass !== 'function' && superClass !== null) { throw new TypeError('Super expression must either be null or a function, not ' + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n var FORWARD = _mobiledocKitUtilsKey.DIRECTION.FORWARD;\n var BACKWARD = _mobiledocKitUtilsKey.DIRECTION.BACKWARD;\n\n var WORD_CHAR_REGEX = /\\w|_|:/;\n\n function findParentSectionFromNode(renderTree, node) {\n var renderNode = renderTree.findRenderNodeFromElement(node, function (renderNode) {\n return renderNode.postNode.isSection;\n });\n\n return renderNode && renderNode.postNode;\n }\n\n function findOffsetInMarkerable(markerable, node, offset) {\n var offsetInSection = 0;\n var marker = markerable.markers.head;\n while (marker) {\n var markerNode = marker.renderNode.element;\n if (markerNode === node) {\n return offsetInSection + offset;\n } else if (marker.isAtom) {\n if (marker.renderNode.headTextNode === node) {\n return offsetInSection;\n } else if (marker.renderNode.tailTextNode === node) {\n return offsetInSection + 1;\n }\n }\n\n offsetInSection += marker.length;\n marker = marker.next;\n }\n\n return offsetInSection;\n }\n\n function findOffsetInSection(section, node, offset) {\n if (section.isMarkerable) {\n return findOffsetInMarkerable(section, node, offset);\n } else {\n (0, _mobiledocKitUtilsAssert['default'])('findOffsetInSection must be called with markerable or card section', section.isCardSection);\n\n var wrapperNode = section.renderNode.element;\n var endTextNode = wrapperNode.lastChild;\n if (node === endTextNode) {\n return 1;\n }\n return 0;\n }\n }\n\n var Position = undefined,\n BlankPosition = undefined;\n\n Position = (function () {\n /**\n * A position is a logical location (zero-width, or \"collapsed\") in a post,\n * typically between two characters in a section.\n * Two positions (a head and a tail) make up a {@link Range}.\n * @constructor\n */\n\n function Position(section) {\n var offset = arguments.length <= 1 || arguments[1] === undefined ? 0 : arguments[1];\n var isBlank = arguments.length <= 2 || arguments[2] === undefined ? false : arguments[2];\n\n _classCallCheck(this, Position);\n\n if (!isBlank) {\n (0, _mobiledocKitUtilsAssert['default'])('Position must have a section that is addressable by the cursor', section && section.isLeafSection);\n (0, _mobiledocKitUtilsAssert['default'])('Position must have numeric offset', typeof offset === 'number');\n }\n\n this.section = section;\n this.offset = offset;\n this.isBlank = isBlank;\n }\n\n /**\n * @param {integer} x x-position in current viewport\n * @param {integer} y y-position in current viewport\n * @param {Editor} editor\n * @return {Position|null}\n */\n\n _createClass(Position, [{\n key: 'toRange',\n\n /**\n * Returns a range from this position to the given tail. If no explicit\n * tail is given this returns a collapsed range focused on this position.\n * @param {Position} [tail=this] The ending position\n * @return {Range}\n * @public\n */\n value: function toRange() {\n var tail = arguments.length <= 0 || arguments[0] === undefined ? this : arguments[0];\n\n return new _mobiledocKitUtilsCursorRange['default'](this, tail);\n }\n }, {\n key: 'markerIn',\n\n /**\n * Returns the marker in `direction` from this position.\n * If the position is in the middle of a marker, the direction is irrelevant.\n * Otherwise, if the position is at a boundary between two markers, returns the\n * marker to the left if `direction` === BACKWARD and the marker to the right\n * if `direction` === FORWARD (assuming left-to-right text direction).\n * @param {Direction}\n * @return {Marker|undefined}\n */\n value: function markerIn(direction) {\n if (!this.isMarkerable) {\n return;\n }\n\n var marker = this.marker;\n var offsetInMarker = this.offsetInMarker;\n\n if (!marker) {\n return;\n }\n\n if (offsetInMarker > 0 && offsetInMarker < marker.length) {\n return marker;\n } else if (offsetInMarker === 0) {\n return direction === BACKWARD ? marker : marker.prev;\n } else if (offsetInMarker === marker.length) {\n return direction === FORWARD ? marker.next : marker;\n }\n }\n }, {\n key: 'isEqual',\n value: function isEqual(position) {\n return this.section === position.section && this.offset === position.offset;\n }\n\n /**\n * @return {Boolean} If this position is at the head of the post\n */\n }, {\n key: 'isHeadOfPost',\n value: function isHeadOfPost() {\n return this.move(BACKWARD).isEqual(this);\n }\n\n /**\n * @return {Boolean} If this position is at the tail of the post\n */\n }, {\n key: 'isTailOfPost',\n value: function isTailOfPost() {\n return this.move(FORWARD).isEqual(this);\n }\n\n /**\n * @return {Boolean} If this position is at the head of its section\n */\n }, {\n key: 'isHead',\n value: function isHead() {\n return this.isEqual(this.section.headPosition());\n }\n\n /**\n * @return {Boolean} If this position is at the head of its section\n */\n }, {\n key: 'isTail',\n value: function isTail() {\n return this.isEqual(this.section.tailPosition());\n }\n\n /**\n * Move the position 1 unit in `direction`.\n *\n * @param {Number} units to move. > 0 moves right, < 0 moves left\n * @return {Position} Return a new position one unit in the given\n * direction. If the position is moving left and at the beginning of the post,\n * the same position will be returned. Same if the position is moving right and\n * at the end of the post.\n */\n }, {\n key: 'move',\n value: function move(units) {\n (0, _mobiledocKitUtilsAssert['default'])('Must pass integer to Position#move', typeof units === 'number');\n\n if (units < 0) {\n return this.moveLeft().move(++units);\n } else if (units > 0) {\n return this.moveRight().move(--units);\n } else {\n return this;\n }\n }\n\n /**\n * @param {Number} direction (FORWARD or BACKWARD)\n * @return {Position} The result of moving 1 \"word\" unit in `direction`\n */\n }, {\n key: 'moveWord',\n value: function moveWord(direction) {\n var isPostBoundary = direction === BACKWARD ? this.isHeadOfPost() : this.isTailOfPost();\n if (isPostBoundary) {\n return this;\n }\n\n if (!this.isMarkerable) {\n return this.move(direction);\n }\n\n var pos = this;\n\n // Helper fn to check if the pos is at the `dir` boundary of its section\n var isBoundary = function isBoundary(pos, dir) {\n return dir === BACKWARD ? pos.isHead() : pos.isTail();\n };\n // Get the char at this position (looking forward/right)\n var getChar = function getChar(pos) {\n var marker = pos.marker;\n var offsetInMarker = pos.offsetInMarker;\n\n return marker.charAt(offsetInMarker);\n };\n // Get the char in `dir` at this position\n var peekChar = function peekChar(pos, dir) {\n return dir === BACKWARD ? getChar(pos.move(BACKWARD)) : getChar(pos);\n };\n // Whether there is an atom in `dir` from this position\n var isAtom = function isAtom(pos, dir) {\n // Special case when position is at end, the marker associated with it is\n // the marker to its left. Normally `pos#marker` is the marker to the right of the pos's offset.\n if (dir === BACKWARD && pos.isTail() && pos.marker.isAtom) {\n return true;\n }\n return dir === BACKWARD ? pos.move(BACKWARD).marker.isAtom : pos.marker.isAtom;\n };\n\n if (isBoundary(pos, direction)) {\n // extend movement into prev/next section\n return pos.move(direction).moveWord(direction);\n }\n\n var seekWord = function seekWord(pos) {\n return !isBoundary(pos, direction) && !isAtom(pos, direction) && !WORD_CHAR_REGEX.test(peekChar(pos, direction));\n };\n\n // move(dir) while we are seeking the first word char\n while (seekWord(pos)) {\n pos = pos.move(direction);\n }\n\n if (isAtom(pos, direction)) {\n return pos.move(direction);\n }\n\n var seekBoundary = function seekBoundary(pos) {\n return !isBoundary(pos, direction) && !isAtom(pos, direction) && WORD_CHAR_REGEX.test(peekChar(pos, direction));\n };\n\n // move(dir) while we are seeking the first boundary position\n while (seekBoundary(pos)) {\n pos = pos.move(direction);\n }\n\n return pos;\n }\n\n /**\n * The position to the left of this position.\n * If this position is the post's headPosition it returns itself.\n * @return {Position}\n * @private\n */\n }, {\n key: 'moveLeft',\n value: function moveLeft() {\n if (this.isHead()) {\n var prev = this.section.previousLeafSection();\n return prev ? prev.tailPosition() : this;\n } else {\n var offset = this.offset - 1;\n if (this.isMarkerable && this.marker) {\n var code = this.marker.value.charCodeAt(offset);\n if (code >= _mobiledocKitModelsMarker.LOW_SURROGATE_RANGE[0] && code <= _mobiledocKitModelsMarker.LOW_SURROGATE_RANGE[1]) {\n offset = offset - 1;\n }\n }\n return new Position(this.section, offset);\n }\n }\n\n /**\n * The position to the right of this position.\n * If this position is the post's tailPosition it returns itself.\n * @return {Position}\n * @private\n */\n }, {\n key: 'moveRight',\n value: function moveRight() {\n if (this.isTail()) {\n var next = this.section.nextLeafSection();\n return next ? next.headPosition() : this;\n } else {\n var offset = this.offset + 1;\n if (this.isMarkerable && this.marker) {\n var code = this.marker.value.charCodeAt(offset - 1);\n if (code >= _mobiledocKitModelsMarker.HIGH_SURROGATE_RANGE[0] && code <= _mobiledocKitModelsMarker.HIGH_SURROGATE_RANGE[1]) {\n offset = offset + 1;\n }\n }\n return new Position(this.section, offset);\n }\n }\n }, {\n key: 'leafSectionIndex',\n get: function get() {\n var _this = this;\n\n var post = this.section.post;\n var leafSectionIndex = undefined;\n post.walkAllLeafSections(function (section, index) {\n if (section === _this.section) {\n leafSectionIndex = index;\n }\n });\n return leafSectionIndex;\n }\n }, {\n key: 'isMarkerable',\n get: function get() {\n return this.section && this.section.isMarkerable;\n }\n\n /**\n * Returns the marker at this position, in the backward direction\n * (i.e., the marker to the left of the cursor if the cursor is on a marker boundary and text is left-to-right)\n * @return {Marker|undefined}\n */\n }, {\n key: 'marker',\n get: function get() {\n return this.isMarkerable && this.markerPosition.marker;\n }\n }, {\n key: 'offsetInMarker',\n get: function get() {\n return this.markerPosition.offset;\n }\n }, {\n key: 'markerPosition',\n\n /**\n * @private\n */\n get: function get() {\n (0, _mobiledocKitUtilsAssert['default'])('Cannot get markerPosition without a section', !!this.section);\n (0, _mobiledocKitUtilsAssert['default'])('cannot get markerPosition of a non-markerable', !!this.section.isMarkerable);\n return this.section.markerPositionAtOffset(this.offset);\n }\n }], [{\n key: 'atPoint',\n value: function atPoint(x, y, editor) {\n var _renderTree = editor._renderTree;\n var rootElement = editor.element;\n\n var elementFromPoint = document.elementFromPoint(x, y);\n if (!(0, _mobiledocKitUtilsDomUtils.containsNode)(rootElement, elementFromPoint)) {\n return;\n }\n\n var _findOffsetInNode = (0, _mobiledocKitUtilsSelectionUtils.findOffsetInNode)(elementFromPoint, { left: x, top: y });\n\n var node = _findOffsetInNode.node;\n var offset = _findOffsetInNode.offset;\n\n return Position.fromNode(_renderTree, node, offset);\n }\n }, {\n key: 'blankPosition',\n value: function blankPosition() {\n return new BlankPosition();\n }\n }, {\n key: 'fromNode',\n value: function fromNode(renderTree, node, offset) {\n if ((0, _mobiledocKitUtilsDomUtils.isTextNode)(node)) {\n return Position.fromTextNode(renderTree, node, offset);\n } else {\n return Position.fromElementNode(renderTree, node, offset);\n }\n }\n }, {\n key: 'fromTextNode',\n value: function fromTextNode(renderTree, textNode, offsetInNode) {\n var renderNode = renderTree.getElementRenderNode(textNode);\n var section = undefined,\n offsetInSection = undefined;\n\n if (renderNode) {\n var marker = renderNode.postNode;\n section = marker.section;\n\n (0, _mobiledocKitUtilsAssert['default'])('Could not find parent section for mapped text node \"' + textNode.textContent + '\"', !!section);\n offsetInSection = section.offsetOfMarker(marker, offsetInNode);\n } else {\n // all text nodes should be rendered by markers except:\n // * text nodes inside cards\n // * text nodes created by the browser during text input\n // both of these should have rendered parent sections, though\n section = findParentSectionFromNode(renderTree, textNode);\n (0, _mobiledocKitUtilsAssert['default'])('Could not find parent section for un-mapped text node \"' + textNode.textContent + '\"', !!section);\n\n offsetInSection = findOffsetInSection(section, textNode, offsetInNode);\n }\n\n return new Position(section, offsetInSection);\n }\n }, {\n key: 'fromElementNode',\n value: function fromElementNode(renderTree, elementNode, offset) {\n var position = undefined;\n\n // The browser may change the reported selection to equal the editor's root\n // element if the user clicks an element that is immediately removed,\n // which can happen when clicking to remove a card.\n if (elementNode === renderTree.rootElement) {\n var post = renderTree.rootNode.postNode;\n position = offset === 0 ? post.headPosition() : post.tailPosition();\n } else {\n var section = findParentSectionFromNode(renderTree, elementNode);\n (0, _mobiledocKitUtilsAssert['default'])('Could not find parent section from element node', !!section);\n\n if (section.isCardSection) {\n // Selections in cards are usually made on a text node\n // containing a ‌ on one side or the other of the card but\n // some scenarios (Firefox) will result in selecting the\n // card's wrapper div. If the offset is 2 we've selected\n // the final zwnj and should consider the cursor at the\n // end of the card (offset 1). Otherwise, the cursor is at\n // the start of the card\n position = offset < 2 ? section.headPosition() : section.tailPosition();\n } else {\n\n // In Firefox it is possible for the cursor to be on an atom's wrapper\n // element. (In Chrome/Safari, the browser corrects this to be on\n // one of the text nodes surrounding the wrapper).\n // This code corrects for when the browser reports the cursor position\n // to be on the wrapper element itself\n var renderNode = renderTree.getElementRenderNode(elementNode);\n var postNode = renderNode && renderNode.postNode;\n if (postNode && postNode.isAtom) {\n var sectionOffset = section.offsetOfMarker(postNode);\n if (offset > 1) {\n // we are on the tail side of the atom\n sectionOffset += postNode.length;\n }\n position = new Position(section, sectionOffset);\n } else {\n // The offset is 0 if the cursor is on a non-atom-wrapper element node\n // (e.g., a
tag in a blank markup section)\n position = section.headPosition();\n }\n }\n }\n\n return position;\n }\n }]);\n\n return Position;\n })();\n\n BlankPosition = (function (_Position) {\n _inherits(BlankPosition, _Position);\n\n function BlankPosition() {\n _classCallCheck(this, BlankPosition);\n\n _get(Object.getPrototypeOf(BlankPosition.prototype), 'constructor', this).call(this, null, 0, true);\n }\n\n _createClass(BlankPosition, [{\n key: 'isEqual',\n value: function isEqual(other) {\n return other && other.isBlank;\n }\n }, {\n key: 'toRange',\n value: function toRange() {\n return _mobiledocKitUtilsCursorRange['default'].blankRange();\n }\n }, {\n key: 'isHeadOfPost',\n value: function isHeadOfPost() {\n return false;\n }\n }, {\n key: 'isTailOfPost',\n value: function isTailOfPost() {\n return false;\n }\n }, {\n key: 'isHead',\n value: function isHead() {\n return false;\n }\n }, {\n key: 'isTail',\n value: function isTail() {\n return false;\n }\n }, {\n key: 'move',\n value: function move() {\n return this;\n }\n }, {\n key: 'moveWord',\n value: function moveWord() {\n return this;\n }\n }, {\n key: 'leafSectionIndex',\n get: function get() {\n (0, _mobiledocKitUtilsAssert['default'])('must implement get leafSectionIndex', false);\n }\n }, {\n key: 'isMarkerable',\n get: function get() {\n return false;\n }\n }, {\n key: 'marker',\n get: function get() {\n return false;\n }\n }, {\n key: 'markerPosition',\n get: function get() {\n return {};\n }\n }]);\n\n return BlankPosition;\n })(Position);\n\n exports['default'] = Position;\n});","define('mobiledoc-kit/utils/cursor/range', ['exports', 'mobiledoc-kit/utils/cursor/position', 'mobiledoc-kit/utils/key', 'mobiledoc-kit/utils/assert'], function (exports, _mobiledocKitUtilsCursorPosition, _mobiledocKitUtilsKey, _mobiledocKitUtilsAssert) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n /**\n * A logical range of a {@link Post}.\n * Usually an instance of Range will be read from the {@link Editor#range} property,\n * but it may be useful to instantiate a range directly when programmatically modifying a Post.\n */\n\n var Range = (function () {\n /**\n * @param {Position} head\n * @param {Position} [tail=head]\n * @param {Direction} [direction=null]\n * @return {Range}\n * @private\n */\n\n function Range(head) {\n var tail = arguments.length <= 1 || arguments[1] === undefined ? head : arguments[1];\n var direction = arguments.length <= 2 || arguments[2] === undefined ? null : arguments[2];\n return (function () {\n _classCallCheck(this, Range);\n\n /** @property {Position} head */\n this.head = head;\n\n /** @property {Position} tail */\n this.tail = tail;\n\n /** @property {Direction} direction */\n this.direction = direction;\n }).apply(this, arguments);\n }\n\n /**\n * Shorthand to create a new range from a section(s) and offset(s).\n * When given only a head section and offset, creates a collapsed range.\n * @param {Section} headSection\n * @param {number} headOffset\n * @param {Section} [tailSection=headSection]\n * @param {number} [tailOffset=headOffset]\n * @param {Direction} [direction=null]\n * @return {Range}\n */\n\n _createClass(Range, [{\n key: 'trimTo',\n\n /**\n * @param {Markerable} section\n * @return {Range} A range that is constrained to only the part that\n * includes the section.\n * FIXME -- if the section isn't the head or tail, it's assumed to be\n * wholly contained. It's possible to call `trimTo` with a selection that is\n * outside of the range, though, which would invalidate that assumption.\n * There's no efficient way to determine if a section is within a range, yet.\n * @private\n */\n value: function trimTo(section) {\n var length = section.length;\n\n var headOffset = section === this.head.section ? Math.min(this.head.offset, length) : 0;\n var tailOffset = section === this.tail.section ? Math.min(this.tail.offset, length) : length;\n\n return Range.create(section, headOffset, section, tailOffset);\n }\n\n /**\n * Expands the range 1 unit in the given direction\n * If the range is expandable in the given direction, always returns a\n * non-collapsed range.\n * @param {Number} units If units is > 0, the range is extended to the right,\n * otherwise range is extended to the left.\n * @return {Range}\n * @public\n */\n }, {\n key: 'extend',\n value: function extend(units) {\n (0, _mobiledocKitUtilsAssert['default'])('Must pass integer to Range#extend', typeof units === 'number');\n\n if (units === 0) {\n return this;\n }\n\n var head = this.head;\n var tail = this.tail;\n var currentDirection = this.direction;\n\n switch (currentDirection) {\n case _mobiledocKitUtilsKey.DIRECTION.FORWARD:\n return new Range(head, tail.move(units), currentDirection);\n case _mobiledocKitUtilsKey.DIRECTION.BACKWARD:\n return new Range(head.move(units), tail, currentDirection);\n default:\n var newDirection = units > 0 ? _mobiledocKitUtilsKey.DIRECTION.FORWARD : _mobiledocKitUtilsKey.DIRECTION.BACKWARD;\n return new Range(head, tail, newDirection).extend(units);\n }\n }\n\n /**\n * Moves this range 1 unit in the given direction.\n * If the range is collapsed, returns a collapsed range shifted by 1 unit,\n * otherwise collapses this range to the position at the `direction` end of the range.\n * Always returns a collapsed range.\n * @param {Direction} direction\n * @return {Range}\n * @public\n */\n }, {\n key: 'move',\n value: function move(direction) {\n (0, _mobiledocKitUtilsAssert['default'])('Must pass DIRECTION.FORWARD (' + _mobiledocKitUtilsKey.DIRECTION.FORWARD + ') or DIRECTION.BACKWARD (' + _mobiledocKitUtilsKey.DIRECTION.BACKWARD + ') to Range#move', direction === _mobiledocKitUtilsKey.DIRECTION.FORWARD || direction === _mobiledocKitUtilsKey.DIRECTION.BACKWARD);\n\n var focusedPosition = this.focusedPosition;\n var isCollapsed = this.isCollapsed;\n\n if (isCollapsed) {\n return new Range(focusedPosition.move(direction));\n } else {\n return this._collapse(direction);\n }\n }\n }, {\n key: '_collapse',\n value: function _collapse(direction) {\n return new Range(direction === _mobiledocKitUtilsKey.DIRECTION.BACKWARD ? this.head : this.tail);\n }\n }, {\n key: 'isEqual',\n value: function isEqual(other) {\n return other && this.head.isEqual(other.head) && this.tail.isEqual(other.tail);\n }\n }, {\n key: 'focusedPosition',\n get: function get() {\n return this.direction === _mobiledocKitUtilsKey.DIRECTION.BACKWARD ? this.head : this.tail;\n }\n }, {\n key: 'isBlank',\n get: function get() {\n return this.head.isBlank && this.tail.isBlank;\n }\n\n // \"legacy\" APIs\n }, {\n key: 'headSection',\n get: function get() {\n return this.head.section;\n }\n }, {\n key: 'tailSection',\n get: function get() {\n return this.tail.section;\n }\n }, {\n key: 'headSectionOffset',\n get: function get() {\n return this.head.offset;\n }\n }, {\n key: 'tailSectionOffset',\n get: function get() {\n return this.tail.offset;\n }\n }, {\n key: 'isCollapsed',\n get: function get() {\n return this.head.isEqual(this.tail);\n }\n }, {\n key: 'headMarker',\n get: function get() {\n return this.head.marker;\n }\n }, {\n key: 'tailMarker',\n get: function get() {\n return this.tail.marker;\n }\n }, {\n key: 'headMarkerOffset',\n get: function get() {\n return this.head.offsetInMarker;\n }\n }, {\n key: 'tailMarkerOffset',\n get: function get() {\n return this.tail.offsetInMarker;\n }\n }], [{\n key: 'create',\n value: function create(headSection, headOffset) {\n var tailSection = arguments.length <= 2 || arguments[2] === undefined ? headSection : arguments[2];\n var tailOffset = arguments.length <= 3 || arguments[3] === undefined ? headOffset : arguments[3];\n var direction = arguments.length <= 4 || arguments[4] === undefined ? null : arguments[4];\n return (function () {\n return new Range(new _mobiledocKitUtilsCursorPosition['default'](headSection, headOffset), new _mobiledocKitUtilsCursorPosition['default'](tailSection, tailOffset), direction);\n })();\n }\n }, {\n key: 'blankRange',\n value: function blankRange() {\n return new Range(_mobiledocKitUtilsCursorPosition['default'].blankPosition(), _mobiledocKitUtilsCursorPosition['default'].blankPosition());\n }\n }]);\n\n return Range;\n })();\n\n exports['default'] = Range;\n});","define(\"mobiledoc-kit/utils/deprecate\", [\"exports\"], function (exports) {\n /**\n * Usage:\n * Without a conditional, always prints deprecate message:\n * `deprecate('This is deprecated')`\n *\n * Conditional deprecation, works similarly to `assert`, prints deprecation if\n * conditional is false:\n * `deprecate('Deprecated only if foo !== bar', foo === bar)`\n */\n \"use strict\";\n\n exports[\"default\"] = deprecate;\n\n function deprecate(message) {\n var conditional = arguments.length <= 1 || arguments[1] === undefined ? false : arguments[1];\n\n if (!conditional) {\n console.log(\"[mobiledoc-kit] [DEPRECATED]: \" + message); // jshint ignore:line\n }\n }\n});","define('mobiledoc-kit/utils/dom-utils', ['exports', 'mobiledoc-kit/utils/array-utils'], function (exports, _mobiledocKitUtilsArrayUtils) {\n 'use strict';\n\n var NODE_TYPES = {\n ELEMENT: 1,\n TEXT: 3,\n COMMENT: 8\n };\n\n exports.NODE_TYPES = NODE_TYPES;\n function isTextNode(node) {\n return node.nodeType === NODE_TYPES.TEXT;\n }\n\n function isCommentNode(node) {\n return node.nodeType === NODE_TYPES.COMMENT;\n }\n\n function isElementNode(node) {\n return node.nodeType === NODE_TYPES.ELEMENT;\n }\n\n // perform a pre-order tree traversal of the dom, calling `callbackFn(node)`\n // for every node for which `conditionFn(node)` is true\n function walkDOM(topNode) {\n var callbackFn = arguments.length <= 1 || arguments[1] === undefined ? function () {} : arguments[1];\n var conditionFn = arguments.length <= 2 || arguments[2] === undefined ? function () {\n return true;\n } : arguments[2];\n\n var currentNode = topNode;\n\n if (conditionFn(currentNode)) {\n callbackFn(currentNode);\n }\n\n currentNode = currentNode.firstChild;\n\n while (currentNode) {\n walkDOM(currentNode, callbackFn, conditionFn);\n currentNode = currentNode.nextSibling;\n }\n }\n\n function walkTextNodes(topNode) {\n var callbackFn = arguments.length <= 1 || arguments[1] === undefined ? function () {} : arguments[1];\n\n var conditionFn = function conditionFn(node) {\n return isTextNode(node);\n };\n walkDOM(topNode, callbackFn, conditionFn);\n }\n\n function clearChildNodes(element) {\n while (element.childNodes.length) {\n element.removeChild(element.childNodes[0]);\n }\n }\n\n /**\n * @return {Boolean} true when the child node is contained or the same as\n * (e.g., inclusive containment) the parent node\n * see https://github.com/webmodules/node-contains/blob/master/index.js\n * Mimics the behavior of `Node.contains`, which is broken in IE 10\n * @private\n */\n function containsNode(parentNode, childNode) {\n if (parentNode === childNode) {\n return true;\n }\n var position = parentNode.compareDocumentPosition(childNode);\n return !!(position & Node.DOCUMENT_POSITION_CONTAINED_BY);\n }\n\n /**\n * converts the element's NamedNodeMap of attrs into\n * an object with key-value pairs\n * @param {DOMNode} element\n * @return {Object} key-value pairs\n * @private\n */\n function getAttributes(element) {\n var result = {};\n if (element.hasAttributes()) {\n (0, _mobiledocKitUtilsArrayUtils.forEach)(element.attributes, function (_ref) {\n var name = _ref.name;\n var value = _ref.value;\n\n result[name] = value;\n });\n }\n return result;\n }\n\n function addClassName(element, className) {\n element.classList.add(className);\n }\n\n function removeClassName(element, className) {\n element.classList.remove(className);\n }\n\n function normalizeTagName(tagName) {\n return tagName.toLowerCase();\n }\n\n function parseHTML(html) {\n var div = document.createElement('div');\n div.innerHTML = html;\n return div;\n }\n\n exports.containsNode = containsNode;\n exports.clearChildNodes = clearChildNodes;\n exports.getAttributes = getAttributes;\n exports.walkDOM = walkDOM;\n exports.walkTextNodes = walkTextNodes;\n exports.addClassName = addClassName;\n exports.removeClassName = removeClassName;\n exports.normalizeTagName = normalizeTagName;\n exports.isTextNode = isTextNode;\n exports.isCommentNode = isCommentNode;\n exports.isElementNode = isElementNode;\n exports.parseHTML = parseHTML;\n});","define('mobiledoc-kit/utils/element-map', ['exports', 'mobiledoc-kit/utils/assert'], function (exports, _mobiledocKitUtilsAssert) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n // start at one to make the falsy semantics easier\n var uuidGenerator = 1;\n\n var ElementMap = (function () {\n function ElementMap() {\n _classCallCheck(this, ElementMap);\n\n this._map = {};\n }\n\n _createClass(ElementMap, [{\n key: 'set',\n value: function set(key, value) {\n var uuid = key._uuid;\n if (!uuid) {\n key._uuid = uuid = '' + uuidGenerator++;\n }\n this._map[uuid] = value;\n }\n }, {\n key: 'get',\n value: function get(key) {\n if (key._uuid) {\n return this._map[key._uuid];\n }\n return null;\n }\n }, {\n key: 'remove',\n value: function remove(key) {\n (0, _mobiledocKitUtilsAssert['default'])('tried to fetch a value for an element not seen before', !!key._uuid);\n delete this._map[key._uuid];\n }\n }]);\n\n return ElementMap;\n })();\n\n exports['default'] = ElementMap;\n});","define('mobiledoc-kit/utils/element-utils', ['exports', 'mobiledoc-kit/utils/string-utils', 'mobiledoc-kit/utils/dom-utils'], function (exports, _mobiledocKitUtilsStringUtils, _mobiledocKitUtilsDomUtils) {\n 'use strict';\n\n function getEventTargetMatchingTag(tagName, target, container) {\n tagName = (0, _mobiledocKitUtilsDomUtils.normalizeTagName)(tagName);\n // Traverses up DOM from an event target to find the node matching specifed tag\n while (target && target !== container) {\n if ((0, _mobiledocKitUtilsDomUtils.normalizeTagName)(target.tagName) === tagName) {\n return target;\n }\n target = target.parentNode;\n }\n }\n\n function getElementRelativeOffset(element) {\n var offset = { left: 0, top: -window.pageYOffset };\n var offsetParent = element.offsetParent;\n var offsetParentPosition = window.getComputedStyle(offsetParent).position;\n var offsetParentRect;\n\n if (offsetParentPosition === 'relative') {\n offsetParentRect = offsetParent.getBoundingClientRect();\n offset.left = offsetParentRect.left;\n offset.top = offsetParentRect.top;\n }\n return offset;\n }\n\n function getElementComputedStyleNumericProp(element, prop) {\n return parseFloat(window.getComputedStyle(element)[prop]);\n }\n\n function positionElementToRect(element, rect, topOffset, leftOffset) {\n var relativeOffset = getElementRelativeOffset(element);\n var style = element.style;\n var round = Math.round;\n var left, top;\n\n topOffset = topOffset || 0;\n leftOffset = leftOffset || 0;\n left = round(rect.left - relativeOffset.left - leftOffset);\n top = round(rect.top - relativeOffset.top - topOffset);\n style.left = left + 'px';\n style.top = top + 'px';\n return { left: left, top: top };\n }\n\n function positionElementHorizontallyCenteredToRect(element, rect, topOffset) {\n var horizontalCenter = element.offsetWidth / 2 - rect.width / 2;\n return positionElementToRect(element, rect, topOffset, horizontalCenter);\n }\n\n function positionElementCenteredBelow(element, belowElement) {\n var elementMargin = getElementComputedStyleNumericProp(element, 'marginTop');\n return positionElementHorizontallyCenteredToRect(element, belowElement.getBoundingClientRect(), -element.offsetHeight - elementMargin);\n }\n\n function setData(element, name, value) {\n if (element.dataset) {\n element.dataset[name] = value;\n } else {\n var dataName = (0, _mobiledocKitUtilsStringUtils.dasherize)(name);\n return element.setAttribute(dataName, value);\n }\n }\n\n exports.setData = setData;\n exports.getEventTargetMatchingTag = getEventTargetMatchingTag;\n exports.getElementRelativeOffset = getElementRelativeOffset;\n exports.getElementComputedStyleNumericProp = getElementComputedStyleNumericProp;\n exports.positionElementToRect = positionElementToRect;\n exports.positionElementHorizontallyCenteredToRect = positionElementHorizontallyCenteredToRect;\n exports.positionElementCenteredBelow = positionElementCenteredBelow;\n});","define(\"mobiledoc-kit/utils/fixed-queue\", [\"exports\"], function (exports) {\n \"use strict\";\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if (\"value\" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError(\"Cannot call a class as a function\"); } }\n\n var FixedQueue = (function () {\n function FixedQueue() {\n var length = arguments.length <= 0 || arguments[0] === undefined ? 0 : arguments[0];\n\n _classCallCheck(this, FixedQueue);\n\n this._maxLength = length;\n this._items = [];\n }\n\n _createClass(FixedQueue, [{\n key: \"pop\",\n value: function pop() {\n return this._items.pop();\n }\n }, {\n key: \"push\",\n value: function push(item) {\n this._items.push(item);\n if (this.length > this._maxLength) {\n this._items.shift();\n }\n }\n }, {\n key: \"clear\",\n value: function clear() {\n this._items = [];\n }\n }, {\n key: \"toArray\",\n value: function toArray() {\n return this._items;\n }\n }, {\n key: \"length\",\n get: function get() {\n return this._items.length;\n }\n }]);\n\n return FixedQueue;\n })();\n\n exports[\"default\"] = FixedQueue;\n});","define('mobiledoc-kit/utils/key', ['exports', 'mobiledoc-kit/utils/keycodes', 'mobiledoc-kit/utils/characters', 'mobiledoc-kit/utils/assert'], function (exports, _mobiledocKitUtilsKeycodes, _mobiledocKitUtilsCharacters, _mobiledocKitUtilsAssert) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n exports.modifierMask = modifierMask;\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n /**\n * @typedef Direction\n * @enum {number}\n * @property {number} FORWARD\n * @property {number} BACKWARD\n */\n var DIRECTION = {\n FORWARD: 1,\n BACKWARD: -1\n };\n exports.DIRECTION = DIRECTION;\n var MODIFIERS = {\n META: 1, // also called \"command\" on OS X\n CTRL: 2,\n SHIFT: 4,\n ALT: 8 // also called \"option\" on OS X\n };\n\n exports.MODIFIERS = MODIFIERS;\n\n function modifierMask(event) {\n var metaKey = event.metaKey;\n var shiftKey = event.shiftKey;\n var ctrlKey = event.ctrlKey;\n var altKey = event.altKey;\n\n var modVal = function modVal(val, modifier) {\n return val && modifier || 0;\n };\n return modVal(metaKey, MODIFIERS.META) + modVal(shiftKey, MODIFIERS.SHIFT) + modVal(ctrlKey, MODIFIERS.CTRL) + modVal(altKey, MODIFIERS.ALT);\n }\n\n var SPECIAL_KEYS = {\n BACKSPACE: _mobiledocKitUtilsKeycodes['default'].BACKSPACE,\n TAB: _mobiledocKitUtilsKeycodes['default'].TAB,\n ENTER: _mobiledocKitUtilsKeycodes['default'].ENTER,\n ESC: _mobiledocKitUtilsKeycodes['default'].ESC,\n SPACE: _mobiledocKitUtilsKeycodes['default'].SPACE,\n PAGEUP: _mobiledocKitUtilsKeycodes['default'].PAGEUP,\n PAGEDOWN: _mobiledocKitUtilsKeycodes['default'].PAGEDOWN,\n END: _mobiledocKitUtilsKeycodes['default'].END,\n HOME: _mobiledocKitUtilsKeycodes['default'].HOME,\n LEFT: _mobiledocKitUtilsKeycodes['default'].LEFT,\n UP: _mobiledocKitUtilsKeycodes['default'].UP,\n RIGHT: _mobiledocKitUtilsKeycodes['default'].RIGHT,\n DOWN: _mobiledocKitUtilsKeycodes['default'].DOWN,\n INS: _mobiledocKitUtilsKeycodes['default'].INS,\n DEL: _mobiledocKitUtilsKeycodes['default'].DELETE\n };\n\n exports.SPECIAL_KEYS = SPECIAL_KEYS;\n // heuristic for determining if `event` is a key event\n function isKeyEvent(event) {\n return (/^key/.test(event.type)\n );\n }\n\n /**\n * An abstraction around a KeyEvent\n * that key listeners in the editor can use\n * to determine what sort of key was pressed\n */\n var Key = (function () {\n function Key(event) {\n _classCallCheck(this, Key);\n\n this.keyCode = event.keyCode;\n this.charCode = event.charCode;\n this.event = event;\n this.modifierMask = modifierMask(event);\n }\n\n _createClass(Key, [{\n key: 'toString',\n value: function toString() {\n if (this.isTab()) {\n return _mobiledocKitUtilsCharacters.TAB;\n }\n return String.fromCharCode(this.charCode);\n }\n }, {\n key: 'isEscape',\n value: function isEscape() {\n return this.keyCode === _mobiledocKitUtilsKeycodes['default'].ESC;\n }\n }, {\n key: 'isDelete',\n value: function isDelete() {\n return this.keyCode === _mobiledocKitUtilsKeycodes['default'].BACKSPACE || this.keyCode === _mobiledocKitUtilsKeycodes['default'].DELETE;\n }\n }, {\n key: 'isForwardDelete',\n value: function isForwardDelete() {\n return this.keyCode === _mobiledocKitUtilsKeycodes['default'].DELETE;\n }\n }, {\n key: 'isArrow',\n value: function isArrow() {\n return this.isHorizontalArrow() || this.isVerticalArrow();\n }\n }, {\n key: 'isHorizontalArrow',\n value: function isHorizontalArrow() {\n return this.keyCode === _mobiledocKitUtilsKeycodes['default'].LEFT || this.keyCode === _mobiledocKitUtilsKeycodes['default'].RIGHT;\n }\n }, {\n key: 'isHorizontalArrowWithoutModifiersOtherThanShift',\n value: function isHorizontalArrowWithoutModifiersOtherThanShift() {\n return this.isHorizontalArrow() && !(this.ctrlKey || this.metaKey || this.altKey);\n }\n }, {\n key: 'isVerticalArrow',\n value: function isVerticalArrow() {\n return this.keyCode === _mobiledocKitUtilsKeycodes['default'].UP || this.keyCode === _mobiledocKitUtilsKeycodes['default'].DOWN;\n }\n }, {\n key: 'isLeftArrow',\n value: function isLeftArrow() {\n return this.keyCode === _mobiledocKitUtilsKeycodes['default'].LEFT;\n }\n }, {\n key: 'isRightArrow',\n value: function isRightArrow() {\n return this.keyCode === _mobiledocKitUtilsKeycodes['default'].RIGHT;\n }\n }, {\n key: 'isHome',\n value: function isHome() {\n return this.keyCode === _mobiledocKitUtilsKeycodes['default'].HOME;\n }\n }, {\n key: 'isEnd',\n value: function isEnd() {\n return this.keyCode === _mobiledocKitUtilsKeycodes['default'].END;\n }\n }, {\n key: 'isSpace',\n value: function isSpace() {\n return this.keyCode === _mobiledocKitUtilsKeycodes['default'].SPACE;\n }\n }, {\n key: 'isTab',\n value: function isTab() {\n return this.keyCode === _mobiledocKitUtilsKeycodes['default'].TAB;\n }\n }, {\n key: 'isEnter',\n value: function isEnter() {\n return this.keyCode === _mobiledocKitUtilsKeycodes['default'].ENTER;\n }\n\n /**\n * If the shift key is depressed.\n * For example, while holding down meta+shift, pressing the \"v\"\n * key would result in an event whose `Key` had `isShift()` with a truthy value,\n * because the shift key is down when pressing the \"v\".\n * @see {isShiftKey} which checks if the key is actually the shift key itself.\n * @return {bool}\n */\n }, {\n key: 'isShift',\n value: function isShift() {\n return this.shiftKey;\n }\n\n /*\n * If the key is the actual shift key. This is false when the shift key\n * is held down and the source `event` is not the shift key.\n * @see {isShift}\n * @return {bool}\n */\n }, {\n key: 'isShiftKey',\n value: function isShiftKey() {\n return this.keyCode === _mobiledocKitUtilsKeycodes['default'].SHIFT;\n }\n\n /*\n * If the key is the actual alt key (aka \"option\" on mac). This is false when the alt key\n * is held down and the source `event` is not the alt key.\n * @return {bool}\n */\n }, {\n key: 'isAltKey',\n value: function isAltKey() {\n return this.keyCode === _mobiledocKitUtilsKeycodes['default'].ALT;\n }\n\n /*\n * If the key is the actual ctrl key. This is false when the ctrl key\n * is held down and the source `event` is not the ctrl key.\n * @return {bool}\n */\n }, {\n key: 'isCtrlKey',\n value: function isCtrlKey() {\n return this.keyCode === _mobiledocKitUtilsKeycodes['default'].CTRL;\n }\n }, {\n key: 'hasModifier',\n value: function hasModifier(modifier) {\n return modifier & this.modifierMask;\n }\n }, {\n key: 'hasAnyModifier',\n value: function hasAnyModifier() {\n return !!this.modifierMask;\n }\n }, {\n key: 'isPrintable',\n\n /**\n * See https://developer.mozilla.org/en-US/docs/Web/API/KeyboardEvent/keyCode#Printable_keys_in_standard_position\n * and http://stackoverflow.com/a/12467610/137784\n */\n value: function isPrintable() {\n if (this.ctrlKey || this.metaKey) {\n return false;\n }\n\n var code = this.keyCode;\n\n // Firefox calls keypress events for arrow keys, but they should not be\n // considered printable\n if (this.isArrow()) {\n return false;\n }\n\n return code !== 0 || this.toString().length > 0 || code >= _mobiledocKitUtilsKeycodes['default']['0'] && code <= _mobiledocKitUtilsKeycodes['default']['9'] || // number keys\n this.isSpace() || this.isTab() || this.isEnter() || code >= _mobiledocKitUtilsKeycodes['default'].A && code <= _mobiledocKitUtilsKeycodes['default'].Z || // letter keys\n code >= _mobiledocKitUtilsKeycodes['default'].a && code <= _mobiledocKitUtilsKeycodes['default'].z || code >= _mobiledocKitUtilsKeycodes['default'].NUMPAD_0 && code <= _mobiledocKitUtilsKeycodes['default'].NUMPAD_9 || // numpad keys\n code >= _mobiledocKitUtilsKeycodes['default'][';'] && code <= _mobiledocKitUtilsKeycodes['default']['`'] || // punctuation\n code >= _mobiledocKitUtilsKeycodes['default']['['] && code <= _mobiledocKitUtilsKeycodes['default']['\"'] ||\n // FIXME the IME action seems to get lost when we issue an `editor.deleteSelection`\n // before it (in Chrome)\n code === _mobiledocKitUtilsKeycodes['default'].IME;\n }\n }, {\n key: 'direction',\n get: function get() {\n switch (true) {\n case this.isDelete():\n return this.isForwardDelete() ? DIRECTION.FORWARD : DIRECTION.BACKWARD;\n case this.isHorizontalArrow():\n return this.isRightArrow() ? DIRECTION.FORWARD : DIRECTION.BACKWARD;\n }\n }\n }, {\n key: 'ctrlKey',\n get: function get() {\n return MODIFIERS.CTRL & this.modifierMask;\n }\n }, {\n key: 'metaKey',\n get: function get() {\n return MODIFIERS.META & this.modifierMask;\n }\n }, {\n key: 'shiftKey',\n get: function get() {\n return MODIFIERS.SHIFT & this.modifierMask;\n }\n }, {\n key: 'altKey',\n get: function get() {\n return MODIFIERS.ALT & this.modifierMask;\n }\n }], [{\n key: 'fromEvent',\n value: function fromEvent(event) {\n (0, _mobiledocKitUtilsAssert['default'])('Must pass a Key event to Key.fromEvent', event && isKeyEvent(event));\n return new Key(event);\n }\n }]);\n\n return Key;\n })();\n\n exports['default'] = Key;\n});","define('mobiledoc-kit/utils/keycodes', ['exports'], function (exports) {\n 'use strict';\n\n exports['default'] = {\n BACKSPACE: 8,\n SPACE: 32,\n ENTER: 13,\n SHIFT: 16,\n ESC: 27,\n DELETE: 46,\n '0': 48,\n '9': 57,\n A: 65,\n Z: 90,\n a: 97,\n z: 122,\n 'NUMPAD_0': 186,\n 'NUMPAD_9': 111,\n ';': 186,\n '.': 190,\n '`': 192,\n '[': 219,\n '\"': 222,\n\n // Input Method Editor uses multiple keystrokes to display characters.\n // Example on mac: press option-i then i. This fires 2 key events in Chrome\n // with keyCode 229 and displays ˆ and then î.\n // See http://lists.w3.org/Archives/Public/www-dom/2010JulSep/att-0182/keyCode-spec.html#fixed-virtual-key-codes\n IME: 229,\n\n TAB: 9,\n PAGEUP: 33,\n PAGEDOWN: 34,\n END: 35,\n HOME: 36,\n LEFT: 37,\n UP: 38,\n RIGHT: 39,\n DOWN: 40,\n INS: 45,\n META: 91,\n ALT: 18,\n CTRL: 17\n };\n});","define(\"mobiledoc-kit/utils/linked-item\", [\"exports\"], function (exports) {\n \"use strict\";\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError(\"Cannot call a class as a function\"); } }\n\n var LinkedItem = function LinkedItem() {\n _classCallCheck(this, LinkedItem);\n\n this.next = null;\n this.prev = null;\n };\n\n exports[\"default\"] = LinkedItem;\n});","define('mobiledoc-kit/utils/linked-list', ['exports', 'mobiledoc-kit/utils/assert'], function (exports, _mobiledocKitUtilsAssert) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n var PARENT_PROP = '__parent';\n\n var LinkedList = (function () {\n function LinkedList(options) {\n _classCallCheck(this, LinkedList);\n\n this.head = null;\n this.tail = null;\n this.length = 0;\n\n if (options) {\n var adoptItem = options.adoptItem;\n var freeItem = options.freeItem;\n\n this._adoptItem = adoptItem;\n this._freeItem = freeItem;\n }\n }\n\n _createClass(LinkedList, [{\n key: 'adoptItem',\n value: function adoptItem(item) {\n item[PARENT_PROP] = this;\n this.length++;\n if (this._adoptItem) {\n this._adoptItem(item);\n }\n }\n }, {\n key: 'freeItem',\n value: function freeItem(item) {\n item[PARENT_PROP] = null;\n this.length--;\n if (this._freeItem) {\n this._freeItem(item);\n }\n }\n }, {\n key: 'prepend',\n value: function prepend(item) {\n this.insertBefore(item, this.head);\n }\n }, {\n key: 'append',\n value: function append(item) {\n this.insertBefore(item, null);\n }\n }, {\n key: 'insertAfter',\n value: function insertAfter(item, prevItem) {\n var nextItem = prevItem ? prevItem.next : this.head;\n this.insertBefore(item, nextItem);\n }\n }, {\n key: '_ensureItemIsNotAlreadyInList',\n value: function _ensureItemIsNotAlreadyInList(item) {\n (0, _mobiledocKitUtilsAssert['default'])('Cannot insert an item into a list if it is already in a list', !item.next && !item.prev && this.head !== item);\n }\n }, {\n key: 'insertBefore',\n value: function insertBefore(item, nextItem) {\n this._ensureItemIsNotInList(item);\n this.adoptItem(item);\n\n var insertPos = undefined;\n if (nextItem && nextItem.prev) {\n insertPos = 'middle';\n } else if (nextItem) {\n insertPos = 'start';\n } else {\n insertPos = 'end';\n }\n\n switch (insertPos) {\n case 'start':\n if (this.head) {\n item.next = this.head;\n this.head.prev = item;\n }\n this.head = item;\n\n break;\n case 'middle':\n var prevItem = nextItem.prev;\n item.next = nextItem;\n item.prev = prevItem;\n nextItem.prev = item;\n prevItem.next = item;\n\n break;\n case 'end':\n var tail = this.tail;\n item.prev = tail;\n\n if (tail) {\n tail.next = item;\n } else {\n this.head = item;\n }\n this.tail = item;\n\n break;\n }\n }\n }, {\n key: 'remove',\n value: function remove(item) {\n if (!item[PARENT_PROP]) {\n return;\n }\n this._ensureItemIsInThisList(item);\n this.freeItem(item);\n\n var prev = item.prev;\n var next = item.next;\n\n item.prev = null;\n item.next = null;\n\n if (prev) {\n prev.next = next;\n } else {\n this.head = next;\n }\n\n if (next) {\n next.prev = prev;\n } else {\n this.tail = prev;\n }\n }\n }, {\n key: 'forEach',\n value: function forEach(callback) {\n var item = this.head;\n var index = 0;\n while (item) {\n callback(item, index++);\n item = item.next;\n }\n }\n }, {\n key: 'map',\n value: function map(callback) {\n var result = [];\n this.forEach(function (i) {\n return result.push(callback(i));\n });\n return result;\n }\n }, {\n key: 'walk',\n value: function walk(startItem, endItem, callback) {\n var item = startItem || this.head;\n while (item) {\n callback(item);\n if (item === endItem) {\n break;\n }\n item = item.next;\n }\n }\n }, {\n key: 'readRange',\n value: function readRange(startItem, endItem) {\n var items = [];\n this.walk(startItem, endItem, function (item) {\n items.push(item);\n });\n return items;\n }\n }, {\n key: 'toArray',\n value: function toArray() {\n return this.readRange();\n }\n }, {\n key: 'detect',\n value: function detect(callback) {\n var item = arguments.length <= 1 || arguments[1] === undefined ? this.head : arguments[1];\n\n while (item) {\n if (callback(item)) {\n return item;\n }\n item = item.next;\n }\n }\n }, {\n key: 'any',\n value: function any(callback) {\n return !!this.detect(callback);\n }\n }, {\n key: 'every',\n value: function every(callback) {\n var item = this.head;\n while (item) {\n if (!callback(item)) {\n return false;\n }\n item = item.next;\n }\n return true;\n }\n }, {\n key: 'objectAt',\n value: function objectAt(targetIndex) {\n var index = -1;\n return this.detect(function () {\n index++;\n return targetIndex === index;\n });\n }\n }, {\n key: 'splice',\n value: function splice(targetItem, removalCount, newItems) {\n var _this = this;\n\n var item = targetItem;\n var nextItem = item.next;\n var count = 0;\n while (item && count < removalCount) {\n count++;\n nextItem = item.next;\n this.remove(item);\n item = nextItem;\n }\n newItems.forEach(function (newItem) {\n _this.insertBefore(newItem, nextItem);\n });\n }\n }, {\n key: 'removeBy',\n value: function removeBy(conditionFn) {\n var item = this.head;\n while (item) {\n var nextItem = item.next;\n\n if (conditionFn(item)) {\n this.remove(item);\n }\n\n item = nextItem;\n }\n }\n }, {\n key: '_ensureItemIsNotInList',\n value: function _ensureItemIsNotInList(item) {\n (0, _mobiledocKitUtilsAssert['default'])('Cannot insert an item into a list if it is already in a list', !item[PARENT_PROP]);\n }\n }, {\n key: '_ensureItemIsInThisList',\n value: function _ensureItemIsInThisList(item) {\n (0, _mobiledocKitUtilsAssert['default'])('Cannot remove item that is in another list', item[PARENT_PROP] === this);\n }\n }, {\n key: 'isEmpty',\n get: function get() {\n return this.length === 0;\n }\n }]);\n\n return LinkedList;\n })();\n\n exports['default'] = LinkedList;\n});","define(\"mobiledoc-kit/utils/log-manager\", [\"exports\"], function (exports) {\n \"use strict\";\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if (\"value\" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError(\"Cannot call a class as a function\"); } }\n\n var Logger = (function () {\n function Logger(type, manager) {\n _classCallCheck(this, Logger);\n\n this.type = type;\n this.manager = manager;\n }\n\n _createClass(Logger, [{\n key: \"isEnabled\",\n value: function isEnabled() {\n return this.manager.isEnabled(this.type);\n }\n }, {\n key: \"log\",\n value: function log() {\n for (var _len = arguments.length, args = Array(_len), _key = 0; _key < _len; _key++) {\n args[_key] = arguments[_key];\n }\n\n args.unshift(\"[\" + this.type + \"]\");\n if (this.isEnabled()) {\n var _window$console;\n\n (_window$console = window.console).log.apply(_window$console, args);\n }\n }\n }]);\n\n return Logger;\n })();\n\n var LogManager = (function () {\n function LogManager() {\n _classCallCheck(this, LogManager);\n\n this.enabledTypes = [];\n this.allEnabled = false;\n }\n\n _createClass(LogManager, [{\n key: \"for\",\n value: function _for(type) {\n return new Logger(type, this);\n }\n }, {\n key: \"enableAll\",\n value: function enableAll() {\n this.allEnabled = true;\n }\n }, {\n key: \"enableTypes\",\n value: function enableTypes(types) {\n this.enabledTypes = this.enabledTypes.concat(types);\n }\n }, {\n key: \"disable\",\n value: function disable() {\n this.enabledTypes = [];\n this.allEnabled = false;\n }\n }, {\n key: \"isEnabled\",\n value: function isEnabled(type) {\n return this.allEnabled || this.enabledTypes.indexOf(type) !== -1;\n }\n }]);\n\n return LogManager;\n })();\n\n exports[\"default\"] = LogManager;\n});","define('mobiledoc-kit/utils/markuperable', ['exports', 'mobiledoc-kit/utils/dom-utils', 'mobiledoc-kit/utils/array-utils'], function (exports, _mobiledocKitUtilsDomUtils, _mobiledocKitUtilsArrayUtils) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n var Markerupable = (function () {\n function Markerupable() {\n _classCallCheck(this, Markerupable);\n }\n\n _createClass(Markerupable, [{\n key: 'clearMarkups',\n value: function clearMarkups() {\n this.markups = [];\n }\n }, {\n key: 'addMarkup',\n value: function addMarkup(markup) {\n this.markups.push(markup);\n }\n }, {\n key: 'addMarkupAtIndex',\n value: function addMarkupAtIndex(markup, index) {\n this.markups.splice(index, 0, markup);\n }\n }, {\n key: 'removeMarkup',\n value: function removeMarkup(markupOrMarkupCallback) {\n var _this = this;\n\n var callback = undefined;\n if (typeof markupOrMarkupCallback === 'function') {\n callback = markupOrMarkupCallback;\n } else {\n (function () {\n var markup = markupOrMarkupCallback;\n callback = function (_markup) {\n return _markup === markup;\n };\n })();\n }\n\n (0, _mobiledocKitUtilsArrayUtils.forEach)((0, _mobiledocKitUtilsArrayUtils.filter)(this.markups, callback), function (m) {\n return _this._removeMarkup(m);\n });\n }\n }, {\n key: '_removeMarkup',\n value: function _removeMarkup(markup) {\n var index = this.markups.indexOf(markup);\n if (index !== -1) {\n this.markups.splice(index, 1);\n }\n }\n }, {\n key: 'hasMarkup',\n value: function hasMarkup(tagNameOrMarkup) {\n return !!this.getMarkup(tagNameOrMarkup);\n }\n }, {\n key: 'getMarkup',\n value: function getMarkup(tagNameOrMarkup) {\n var _this2 = this;\n\n if (typeof tagNameOrMarkup === 'string') {\n var _ret2 = (function () {\n var tagName = (0, _mobiledocKitUtilsDomUtils.normalizeTagName)(tagNameOrMarkup);\n return {\n v: (0, _mobiledocKitUtilsArrayUtils.detect)(_this2.markups, function (markup) {\n return markup.tagName === tagName;\n })\n };\n })();\n\n if (typeof _ret2 === 'object') return _ret2.v;\n } else {\n var _ret3 = (function () {\n var targetMarkup = tagNameOrMarkup;\n return {\n v: (0, _mobiledocKitUtilsArrayUtils.detect)(_this2.markups, function (markup) {\n return markup === targetMarkup;\n })\n };\n })();\n\n if (typeof _ret3 === 'object') return _ret3.v;\n }\n }\n }, {\n key: 'openedMarkups',\n get: function get() {\n var count = 0;\n if (this.prev) {\n count = (0, _mobiledocKitUtilsArrayUtils.commonItemLength)(this.markups, this.prev.markups);\n }\n\n return this.markups.slice(count);\n }\n }, {\n key: 'closedMarkups',\n get: function get() {\n var count = 0;\n if (this.next) {\n count = (0, _mobiledocKitUtilsArrayUtils.commonItemLength)(this.markups, this.next.markups);\n }\n\n return this.markups.slice(count);\n }\n }]);\n\n return Markerupable;\n })();\n\n exports['default'] = Markerupable;\n});","define(\"mobiledoc-kit/utils/merge\", [\"exports\"], function (exports) {\n \"use strict\";\n\n function mergeWithOptions(original, updates, options) {\n options = options || {};\n for (var prop in updates) {\n if (options.hasOwnProperty(prop)) {\n original[prop] = options[prop];\n } else if (updates.hasOwnProperty(prop)) {\n original[prop] = updates[prop];\n }\n }\n return original;\n }\n\n /**\n * Merges properties of one object into another\n * @private\n */\n function merge(original, updates) {\n return mergeWithOptions(original, updates);\n }\n\n exports.mergeWithOptions = mergeWithOptions;\n exports.merge = merge;\n});","define('mobiledoc-kit/utils/mixin', ['exports'], function (exports) {\n 'use strict';\n\n exports['default'] = mixin;\n var CONSTRUCTOR_FN_NAME = 'constructor';\n\n function mixin(target, source) {\n target = target.prototype;\n // Fallback to just `source` to allow mixing in a plain object (pojo)\n source = source.prototype || source;\n\n Object.getOwnPropertyNames(source).forEach(function (name) {\n if (name !== CONSTRUCTOR_FN_NAME) {\n var descriptor = Object.getOwnPropertyDescriptor(source, name);\n\n Object.defineProperty(target, name, descriptor);\n }\n });\n }\n});","define('mobiledoc-kit/utils/mobiledoc-error', ['exports'], function (exports) {\n 'use strict';\n\n var errorProps = ['description', 'fileName', 'lineNumber', 'message', 'name', 'number', 'stack'];\n\n function MobiledocError() {\n var tmp = Error.apply(this, arguments);\n\n if (Error.captureStackTrace) {\n Error.captureStackTrace(this, this.constructor);\n }\n // Unfortunately errors are not enumerable in Chrome (at least), so `for prop in tmp` doesn't work.\n for (var idx = 0; idx < errorProps.length; idx++) {\n this[errorProps[idx]] = tmp[errorProps[idx]];\n }\n }\n\n MobiledocError.prototype = Object.create(Error.prototype);\n\n exports['default'] = MobiledocError;\n});","define('mobiledoc-kit/utils/parse-utils', ['exports', 'mobiledoc-kit/parsers/mobiledoc', 'mobiledoc-kit/parsers/html', 'mobiledoc-kit/parsers/text'], function (exports, _mobiledocKitParsersMobiledoc, _mobiledocKitParsersHtml, _mobiledocKitParsersText) {\n /* global JSON */\n 'use strict';\n\n exports.getContentFromPasteEvent = getContentFromPasteEvent;\n exports.setClipboardData = setClipboardData;\n exports.parsePostFromPaste = parsePostFromPaste;\n exports.parsePostFromDrop = parsePostFromDrop;\n var MIME_TEXT_PLAIN = 'text/plain';\n exports.MIME_TEXT_PLAIN = MIME_TEXT_PLAIN;\n var MIME_TEXT_HTML = 'text/html';\n exports.MIME_TEXT_HTML = MIME_TEXT_HTML;\n var NONSTANDARD_IE_TEXT_TYPE = 'Text';\n\n exports.NONSTANDARD_IE_TEXT_TYPE = NONSTANDARD_IE_TEXT_TYPE;\n var MOBILEDOC_REGEX = new RegExp(/data\\-mobiledoc='(.*?)'>/);\n\n /**\n * @return {Post}\n * @private\n */\n function parsePostFromHTML(html, builder, plugins) {\n var post = undefined;\n\n if (MOBILEDOC_REGEX.test(html)) {\n var mobiledocString = html.match(MOBILEDOC_REGEX)[1];\n var mobiledoc = JSON.parse(mobiledocString);\n post = _mobiledocKitParsersMobiledoc['default'].parse(builder, mobiledoc);\n } else {\n post = new _mobiledocKitParsersHtml['default'](builder, { plugins: plugins }).parse(html);\n }\n\n return post;\n }\n\n /**\n * @return {Post}\n * @private\n */\n function parsePostFromText(text, builder, plugins) {\n var parser = new _mobiledocKitParsersText['default'](builder, { plugins: plugins });\n var post = parser.parse(text);\n return post;\n }\n\n /**\n * @return {{html: String, text: String}}\n * @private\n */\n\n function getContentFromPasteEvent(event, window) {\n var html = '',\n text = '';\n\n var clipboardData = event.clipboardData;\n\n if (clipboardData && clipboardData.getData) {\n html = clipboardData.getData(MIME_TEXT_HTML);\n text = clipboardData.getData(MIME_TEXT_PLAIN);\n } else if (window.clipboardData && window.clipboardData.getData) {\n // IE\n // The Internet Explorers (including Edge) have a non-standard way of interacting with the\n // Clipboard API (see http://caniuse.com/#feat=clipboard). In short, they expose a global window.clipboardData\n // object instead of the per-event event.clipboardData object on the other browsers.\n html = window.clipboardData.getData(NONSTANDARD_IE_TEXT_TYPE);\n }\n\n return { html: html, text: text };\n }\n\n /**\n * @return {{html: String, text: String}}\n * @private\n */\n function getContentFromDropEvent(event, logger) {\n var html = '',\n text = '';\n\n try {\n html = event.dataTransfer.getData(MIME_TEXT_HTML);\n text = event.dataTransfer.getData(MIME_TEXT_PLAIN);\n } catch (e) {\n // FIXME IE11 does not include any data in the 'text/html' or 'text/plain'\n // mimetypes. It throws an error 'Invalid argument' when attempting to read\n // these properties.\n if (logger) {\n logger.log('Error getting drop data: ', e);\n }\n }\n\n return { html: html, text: text };\n }\n\n /**\n * @param {CopyEvent|CutEvent}\n * @param {Editor}\n * @param {Window}\n * @private\n */\n\n function setClipboardData(event, _ref, window) {\n var mobiledoc = _ref.mobiledoc;\n var html = _ref.html;\n var text = _ref.text;\n\n if (mobiledoc && html) {\n html = '
' + html + '
';\n }\n\n var clipboardData = event.clipboardData;\n var nonstandardClipboardData = window.clipboardData;\n\n if (clipboardData && clipboardData.setData) {\n clipboardData.setData(MIME_TEXT_HTML, html);\n clipboardData.setData(MIME_TEXT_PLAIN, text);\n } else if (nonstandardClipboardData && nonstandardClipboardData.setData) {\n // The Internet Explorers (including Edge) have a non-standard way of interacting with the\n // Clipboard API (see http://caniuse.com/#feat=clipboard). In short, they expose a global window.clipboardData\n // object instead of the per-event event.clipboardData object on the other browsers.\n nonstandardClipboardData.setData(NONSTANDARD_IE_TEXT_TYPE, html);\n }\n }\n\n /**\n * @param {PasteEvent}\n * @param {{builder: Builder, _parserPlugins: Array}} options\n * @return {Post}\n * @private\n */\n\n function parsePostFromPaste(pasteEvent, _ref2) {\n var builder = _ref2.builder;\n var plugins = _ref2._parserPlugins;\n\n var _ref3 = arguments.length <= 2 || arguments[2] === undefined ? { targetFormat: 'html' } : arguments[2];\n\n var targetFormat = _ref3.targetFormat;\n\n var _getContentFromPasteEvent = getContentFromPasteEvent(pasteEvent, window);\n\n var html = _getContentFromPasteEvent.html;\n var text = _getContentFromPasteEvent.text;\n\n if (targetFormat === 'html' && html && html.length) {\n return parsePostFromHTML(html, builder, plugins);\n } else if (text && text.length) {\n return parsePostFromText(text, builder, plugins);\n }\n }\n\n /**\n * @param {DropEvent}\n * @param {Editor} editor\n * @param {Object} [options={}] Can pass a logger\n * @return {Post}\n * @private\n */\n\n function parsePostFromDrop(dropEvent, editor) {\n var _ref4 = arguments.length <= 2 || arguments[2] === undefined ? {} : arguments[2];\n\n var logger = _ref4.logger;\n var builder = editor.builder;\n var plugins = editor._parserPlugins;\n\n var _getContentFromDropEvent = getContentFromDropEvent(dropEvent, logger);\n\n var html = _getContentFromDropEvent.html;\n var text = _getContentFromDropEvent.text;\n\n if (html && html.length) {\n return parsePostFromHTML(html, builder, plugins);\n } else if (text && text.length) {\n return parsePostFromText(text, builder, plugins);\n }\n }\n});","define(\"mobiledoc-kit/utils/placeholder-image-src\", [\"exports\"], function (exports) {\n \"use strict\";\n\n var placeholderImageSrc = \"data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAOEAAADhCAMAAAAJbSJIAAAAMFBMVEXp7vG6vsHm6+63u77Hy868wMPe4+bO09bh5unr8fTR1djAxMfM0NPX3N/c4eTBxcjXRf5TAAACh0lEQVR4nO3b6ZKqMBSFUSQMYZL3f9tbBq/NEEDiqUqOfusn1ZXKbjcQlGQZAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAACC6RkbsGHuabChEtHmiGYfS3EQYM+Sxw/gMQvmcNnYaj6oTDHi73WPn2eqnj9B8zo3TJXcq5uNjXmVff86VwSR3JtryMa1BYqi7S1hJDCVpSigyLcGhJJEwzlCSNtPKrbVhVwsdCfOhH7uuaG3ARV9DwsaOzxt3N1yPqCHhvXytTUz92VDpmE/LLhZwl++R6Sds6sUa/PL6K/2E2fIhw1xdRKefsFolrPc+xNx/N0k/4fpBsdhL2HfeiN+TsDCms8dDpeRyS3P3QDl6Iqaf8L0rTf+80m6Lmn7Ct+4Wxf+/2RY1/YRv3PHz/u+fsCmqgoTnq7Z+8SGviqoh4dnKu1ieqauiakh4/PQ0r6ivqDoSHj0B97eNRVG1JNxV+L4bnxdVecJtRTdFVZ7QU9F1UXUn9FZ0VVRlCav5ob2KLouqKmFjy676u2HsVnRRVFUJq3J+8KCi86IqSthMvyl209Hjijqm3RsqAZ5pNfa5PJ2KelJRjQmr1/r7cfy0ouoSNvOfvbvhvKLaEr4qOin9kTQnrN7LpDZhE/Zmhp6Eq4p+YcKgiipKGFhRRQkDK6ooYfgLbiSMioQkJGF8P5XwHv4O+7AaKiXzaeXh1kMl5AffTUxiKEm/krD94BR8Gdxl1fceSlR58ZhXKbEpyD2amNiBtmrJLTMHL1LF8/rpXkSZXEmz8K8uvAFFNm6Iq0aBLUFOmeCuJ6exrcCmoLpN7kYx891bSAEAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAADgh/wDdr8peyRHLogAAAAASUVORK5CYII=\";\n\n exports[\"default\"] = placeholderImageSrc;\n});","define('mobiledoc-kit/utils/selection-utils', ['exports', 'mobiledoc-kit/utils/key', 'mobiledoc-kit/utils/dom-utils'], function (exports, _mobiledocKitUtilsKey, _mobiledocKitUtilsDomUtils) {\n 'use strict';\n\n function clearSelection() {\n window.getSelection().removeAllRanges();\n }\n\n function textNodeRects(node) {\n var range = document.createRange();\n range.setEnd(node, node.nodeValue.length);\n range.setStart(node, 0);\n return range.getClientRects();\n }\n\n function findOffsetInTextNode(node, coords) {\n var len = node.nodeValue.length;\n var range = document.createRange();\n for (var i = 0; i < len; i++) {\n range.setEnd(node, i + 1);\n range.setStart(node, i);\n var rect = range.getBoundingClientRect();\n if (rect.top === rect.bottom) {\n continue;\n }\n if (rect.left <= coords.left && rect.right >= coords.left && rect.top <= coords.top && rect.bottom >= coords.top) {\n return { node: node, offset: i + (coords.left >= (rect.left + rect.right) / 2 ? 1 : 0) };\n }\n }\n return { node: node, offset: 0 };\n }\n\n /*\n * @param {Object} coords with `top` and `left`\n * @see https://github.com/ProseMirror/prosemirror/blob/4c22e3fe97d87a355a0534e25d65aaf0c0d83e57/src/edit/dompos.js\n * @return {Object} {node, offset}\n */\n function findOffsetInNode(_x, _x2) {\n var _again = true;\n\n _function: while (_again) {\n var node = _x,\n coords = _x2;\n _again = false;\n\n var closest = undefined,\n dyClosest = 1e8,\n coordsClosest = undefined,\n offset = 0;\n for (var child = node.firstChild; child; child = child.nextSibling) {\n var rects = undefined;\n if ((0, _mobiledocKitUtilsDomUtils.isElementNode)(child)) {\n rects = child.getClientRects();\n } else if ((0, _mobiledocKitUtilsDomUtils.isTextNode)(child)) {\n rects = textNodeRects(child);\n } else {\n continue;\n }\n\n for (var i = 0; i < rects.length; i++) {\n var rect = rects[i];\n if (rect.left <= coords.left && rect.right >= coords.left) {\n var dy = rect.top > coords.top ? rect.top - coords.top : rect.bottom < coords.top ? coords.top - rect.bottom : 0;\n if (dy < dyClosest) {\n closest = child;\n dyClosest = dy;\n coordsClosest = dy ? { left: coords.left, top: rect.top } : coords;\n if ((0, _mobiledocKitUtilsDomUtils.isElementNode)(child) && !child.firstChild) {\n offset = i + (coords.left >= (rect.left + rect.right) / 2 ? 1 : 0);\n }\n continue;\n }\n }\n if (!closest && (coords.top >= rect.bottom || coords.top >= rect.top && coords.left >= rect.right)) {\n offset = i + 1;\n }\n }\n }\n if (!closest) {\n return { node: node, offset: offset };\n }\n if ((0, _mobiledocKitUtilsDomUtils.isTextNode)(closest)) {\n return findOffsetInTextNode(closest, coordsClosest);\n }\n if (closest.firstChild) {\n _x = closest;\n _x2 = coordsClosest;\n _again = true;\n closest = dyClosest = coordsClosest = offset = child = rects = i = rect = dy = undefined;\n continue _function;\n }\n return { node: node, offset: offset };\n }\n }\n\n function comparePosition(_x3) {\n var _again2 = true;\n\n _function2: while (_again2) {\n var selection = _x3;\n _again2 = false;\n var anchorNode = selection.anchorNode;\n var focusNode = selection.focusNode;\n var anchorOffset = selection.anchorOffset;\n var focusOffset = selection.focusOffset;\n\n var headNode = undefined,\n tailNode = undefined,\n headOffset = undefined,\n tailOffset = undefined,\n direction = undefined;\n\n var position = anchorNode.compareDocumentPosition(focusNode);\n\n // IE may select return focus and anchor nodes far up the DOM tree instead of\n // picking the deepest, most specific possible node. For example in\n //\n //
abcdef
\n //\n // with a cursor between c and d, IE might say the focusNode is
with\n // an offset of 1. However the anchorNode for a selection might still be\n // 2 if there was a selection.\n //\n // This code walks down the DOM tree until a good comparison of position can be\n // made.\n //\n if (position & Node.DOCUMENT_POSITION_CONTAINS) {\n if (focusOffset < focusNode.childNodes.length) {\n focusNode = focusNode.childNodes[focusOffset];\n focusOffset = 0;\n } else {\n // This situation happens on IE when triple-clicking to select.\n // Set the focus to the very last character inside the node.\n while (focusNode.lastChild) {\n focusNode = focusNode.lastChild;\n }\n focusOffset = focusNode.textContent.length;\n }\n\n _x3 = {\n focusNode: focusNode,\n focusOffset: focusOffset,\n anchorNode: anchorNode, anchorOffset: anchorOffset\n };\n _again2 = true;\n anchorNode = focusNode = anchorOffset = focusOffset = headNode = tailNode = headOffset = tailOffset = direction = position = undefined;\n continue _function2;\n } else if (position & Node.DOCUMENT_POSITION_CONTAINED_BY) {\n var offset = anchorOffset - 1;\n if (offset < 0) {\n offset = 0;\n }\n _x3 = {\n anchorNode: anchorNode.childNodes[offset],\n anchorOffset: 0,\n focusNode: focusNode, focusOffset: focusOffset\n };\n _again2 = true;\n anchorNode = focusNode = anchorOffset = focusOffset = headNode = tailNode = headOffset = tailOffset = direction = position = offset = undefined;\n continue _function2;\n\n // The meat of translating anchor and focus nodes to head and tail nodes\n } else if (position & Node.DOCUMENT_POSITION_FOLLOWING) {\n headNode = anchorNode;tailNode = focusNode;\n headOffset = anchorOffset;tailOffset = focusOffset;\n direction = _mobiledocKitUtilsKey.DIRECTION.FORWARD;\n } else if (position & Node.DOCUMENT_POSITION_PRECEDING) {\n headNode = focusNode;tailNode = anchorNode;\n headOffset = focusOffset;tailOffset = anchorOffset;\n direction = _mobiledocKitUtilsKey.DIRECTION.BACKWARD;\n } else {\n // same node\n headNode = tailNode = anchorNode;\n headOffset = anchorOffset;\n tailOffset = focusOffset;\n if (tailOffset < headOffset) {\n // Swap the offset order\n headOffset = focusOffset;\n tailOffset = anchorOffset;\n direction = _mobiledocKitUtilsKey.DIRECTION.BACKWARD;\n } else if (headOffset < tailOffset) {\n direction = _mobiledocKitUtilsKey.DIRECTION.FORWARD;\n } else {\n direction = null;\n }\n }\n\n return { headNode: headNode, headOffset: headOffset, tailNode: tailNode, tailOffset: tailOffset, direction: direction };\n }\n }\n\n exports.clearSelection = clearSelection;\n exports.comparePosition = comparePosition;\n exports.findOffsetInNode = findOffsetInNode;\n});","define(\"mobiledoc-kit/utils/set\", [\"exports\"], function (exports) {\n \"use strict\";\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if (\"value\" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError(\"Cannot call a class as a function\"); } }\n\n var Set = (function () {\n function Set() {\n var _this = this;\n\n var items = arguments.length <= 0 || arguments[0] === undefined ? [] : arguments[0];\n\n _classCallCheck(this, Set);\n\n this.items = [];\n items.forEach(function (i) {\n return _this.add(i);\n });\n }\n\n _createClass(Set, [{\n key: \"add\",\n value: function add(item) {\n if (!this.has(item)) {\n this.items.push(item);\n }\n }\n }, {\n key: \"has\",\n value: function has(item) {\n return this.items.indexOf(item) !== -1;\n }\n }, {\n key: \"toArray\",\n value: function toArray() {\n return this.items;\n }\n }, {\n key: \"length\",\n get: function get() {\n return this.items.length;\n }\n }]);\n\n return Set;\n })();\n\n exports[\"default\"] = Set;\n});","define('mobiledoc-kit/utils/string-utils', ['exports'], function (exports) {\n /*\n * @param {String} string\n * @return {String} a dasherized string. 'modelIndex' -> 'model-index', etc\n */\n 'use strict';\n\n exports.dasherize = dasherize;\n exports.capitalize = capitalize;\n exports.startsWith = startsWith;\n exports.endsWith = endsWith;\n\n function dasherize(string) {\n return string.replace(/[A-Z]/g, function (match, offset) {\n var lower = match.toLowerCase();\n\n return offset === 0 ? lower : '-' + lower;\n });\n }\n\n function capitalize(string) {\n return string.charAt(0).toUpperCase() + string.slice(1);\n }\n\n function startsWith(string, character) {\n return string.charAt(0) === character;\n }\n\n function endsWith(string, endString) {\n var index = string.lastIndexOf(endString);\n return index !== -1 && index === string.length - endString.length;\n }\n});","define('mobiledoc-kit/utils/to-range', ['exports', 'mobiledoc-kit/utils/cursor/range', 'mobiledoc-kit/utils/cursor/position', 'mobiledoc-kit/utils/assert'], function (exports, _mobiledocKitUtilsCursorRange, _mobiledocKitUtilsCursorPosition, _mobiledocKitUtilsAssert) {\n 'use strict';\n\n exports['default'] = toRange;\n\n function toRange(rangeLike) {\n (0, _mobiledocKitUtilsAssert['default'])('Must pass non-blank object to \"toRange\"', !!rangeLike);\n\n if (rangeLike instanceof _mobiledocKitUtilsCursorRange['default']) {\n return rangeLike;\n } else if (rangeLike instanceof _mobiledocKitUtilsCursorPosition['default']) {\n return rangeLike.toRange();\n }\n\n (0, _mobiledocKitUtilsAssert['default'])('Incorrect structure for rangeLike: ' + rangeLike, false);\n }\n});","define('mobiledoc-kit/version', ['exports'], function (exports) {\n 'use strict';\n\n exports['default'] = '##VERSION##';\n});","define('mobiledoc-kit/views/tooltip', ['exports', 'mobiledoc-kit/views/view', 'mobiledoc-kit/utils/element-utils'], function (exports, _mobiledocKitViewsView, _mobiledocKitUtilsElementUtils) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n var _get = function get(_x, _x2, _x3) { var _again = true; _function: while (_again) { var object = _x, property = _x2, receiver = _x3; _again = false; if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { _x = parent; _x2 = property; _x3 = receiver; _again = true; desc = parent = undefined; continue _function; } } else if ('value' in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } } };\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n function _inherits(subClass, superClass) { if (typeof superClass !== 'function' && superClass !== null) { throw new TypeError('Super expression must either be null or a function, not ' + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }\n\n var DELAY = 200;\n\n var Tooltip = (function (_View) {\n _inherits(Tooltip, _View);\n\n function Tooltip(options) {\n var _this = this;\n\n _classCallCheck(this, Tooltip);\n\n var rootElement = options.rootElement;\n\n var timeout = undefined;\n options.classNames = ['__mobiledoc-tooltip'];\n _get(Object.getPrototypeOf(Tooltip.prototype), 'constructor', this).call(this, options);\n\n this.addEventListener(rootElement, 'mouseover', function (e) {\n var target = (0, _mobiledocKitUtilsElementUtils.getEventTargetMatchingTag)(options.showForTag, e.target, rootElement);\n if (target && target.isContentEditable) {\n timeout = setTimeout(function () {\n _this.showLink(target.href, target);\n }, DELAY);\n }\n });\n\n this.addEventListener(rootElement, 'mouseout', function (e) {\n clearTimeout(timeout);\n var toElement = e.toElement || e.relatedTarget;\n if (toElement && toElement.className !== _this.element.className) {\n _this.hide();\n }\n });\n }\n\n _createClass(Tooltip, [{\n key: 'showMessage',\n value: function showMessage(message, element) {\n var tooltipElement = this.element;\n tooltipElement.innerHTML = message;\n this.show();\n (0, _mobiledocKitUtilsElementUtils.positionElementCenteredBelow)(tooltipElement, element);\n }\n }, {\n key: 'showLink',\n value: function showLink(link, element) {\n var message = '' + link + '';\n this.showMessage(message, element);\n }\n }]);\n\n return Tooltip;\n })(_mobiledocKitViewsView['default']);\n\n exports['default'] = Tooltip;\n});","define('mobiledoc-kit/views/view', ['exports', 'mobiledoc-kit/utils/dom-utils'], function (exports, _mobiledocKitUtilsDomUtils) {\n 'use strict';\n\n var _slicedToArray = (function () { function sliceIterator(arr, i) { var _arr = []; var _n = true; var _d = false; var _e = undefined; try { for (var _i = arr[Symbol.iterator](), _s; !(_n = (_s = _i.next()).done); _n = true) { _arr.push(_s.value); if (i && _arr.length === i) break; } } catch (err) { _d = true; _e = err; } finally { try { if (!_n && _i['return']) _i['return'](); } finally { if (_d) throw _e; } } return _arr; } return function (arr, i) { if (Array.isArray(arr)) { return arr; } else if (Symbol.iterator in Object(arr)) { return sliceIterator(arr, i); } else { throw new TypeError('Invalid attempt to destructure non-iterable instance'); } }; })();\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n var View = (function () {\n function View() {\n var _this = this;\n\n var options = arguments.length <= 0 || arguments[0] === undefined ? {} : arguments[0];\n\n _classCallCheck(this, View);\n\n options.tagName = options.tagName || 'div';\n options.container = options.container || document.body;\n\n this.element = document.createElement(options.tagName);\n this.container = options.container;\n this.isShowing = false;\n\n var classNames = options.classNames || [];\n classNames.forEach(function (name) {\n return (0, _mobiledocKitUtilsDomUtils.addClassName)(_this.element, name);\n });\n this._eventListeners = [];\n }\n\n _createClass(View, [{\n key: 'addEventListener',\n value: function addEventListener(element, type, listener) {\n element.addEventListener(type, listener);\n this._eventListeners.push([element, type, listener]);\n }\n }, {\n key: 'removeAllEventListeners',\n value: function removeAllEventListeners() {\n this._eventListeners.forEach(function (_ref) {\n var _ref2 = _slicedToArray(_ref, 3);\n\n var element = _ref2[0];\n var type = _ref2[1];\n var listener = _ref2[2];\n\n element.removeEventListener(type, listener);\n });\n }\n }, {\n key: 'show',\n value: function show() {\n if (!this.isShowing) {\n this.container.appendChild(this.element);\n this.isShowing = true;\n return true;\n }\n }\n }, {\n key: 'hide',\n value: function hide() {\n if (this.isShowing) {\n this.container.removeChild(this.element);\n this.isShowing = false;\n return true;\n }\n }\n }, {\n key: 'destroy',\n value: function destroy() {\n this.removeAllEventListeners();\n this.hide();\n this.isDestroyed = true;\n }\n }]);\n\n return View;\n })();\n\n exports['default'] = View;\n});","define('mobiledoc-text-renderer/cards/image', ['exports'], function (exports) {\n 'use strict';\n\n exports['default'] = {\n name: 'image-card',\n type: 'text',\n render: function render() {}\n };\n});","define('mobiledoc-text-renderer', ['exports', 'mobiledoc-text-renderer/renderer-factory', 'mobiledoc-text-renderer/utils/render-type'], function (exports, _mobiledocTextRendererRendererFactory, _mobiledocTextRendererUtilsRenderType) {\n 'use strict';\n\n exports.registerGlobal = registerGlobal;\n\n function registerGlobal(window) {\n window.MobiledocTextRenderer = _mobiledocTextRendererRendererFactory['default'];\n }\n\n exports.RENDER_TYPE = _mobiledocTextRendererUtilsRenderType['default'];\n exports['default'] = _mobiledocTextRendererRendererFactory['default'];\n});","define('mobiledoc-text-renderer/renderer-factory', ['exports', 'mobiledoc-text-renderer/renderers/0-2', 'mobiledoc-text-renderer/renderers/0-3', 'mobiledoc-text-renderer/utils/render-type'], function (exports, _mobiledocTextRendererRenderers02, _mobiledocTextRendererRenderers03, _mobiledocTextRendererUtilsRenderType) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n /**\n * runtime Text renderer\n * renders a mobiledoc to Text\n *\n * input: mobiledoc\n * output: Text (string)\n */\n\n function validateCards(cards) {\n if (!Array.isArray(cards)) {\n throw new Error('`cards` must be passed as an array');\n }\n for (var i = 0; i < cards.length; i++) {\n var card = cards[i];\n if (card.type !== _mobiledocTextRendererUtilsRenderType['default']) {\n throw new Error('Card \"' + card.name + '\" must be type \"' + _mobiledocTextRendererUtilsRenderType['default'] + '\", was \"' + card.type + '\"');\n }\n if (!card.render) {\n throw new Error('Card \"' + card.name + '\" must define `render`');\n }\n }\n }\n\n function validateAtoms(atoms) {\n if (!Array.isArray(atoms)) {\n throw new Error('`atoms` must be passed as an array');\n }\n for (var i = 0; i < atoms.length; i++) {\n var atom = atoms[i];\n if (atom.type !== _mobiledocTextRendererUtilsRenderType['default']) {\n throw new Error('Atom \"' + atom.name + '\" must be type \"' + _mobiledocTextRendererUtilsRenderType['default'] + '\", was \"' + atom.type + '\"');\n }\n if (!atom.render) {\n throw new Error('Atom \"' + atom.name + '\" must define `render`');\n }\n }\n }\n\n var RendererFactory = (function () {\n function RendererFactory() {\n var _ref = arguments.length <= 0 || arguments[0] === undefined ? {} : arguments[0];\n\n var cards = _ref.cards;\n var atoms = _ref.atoms;\n var cardOptions = _ref.cardOptions;\n var unknownCardHandler = _ref.unknownCardHandler;\n var unknownAtomHandler = _ref.unknownAtomHandler;\n\n _classCallCheck(this, RendererFactory);\n\n cards = cards || [];\n validateCards(cards);\n atoms = atoms || [];\n validateAtoms(atoms);\n cardOptions = cardOptions || {};\n\n this.state = { cards: cards, atoms: atoms, cardOptions: cardOptions, unknownCardHandler: unknownCardHandler, unknownAtomHandler: unknownAtomHandler };\n }\n\n _createClass(RendererFactory, [{\n key: 'render',\n value: function render(mobiledoc) {\n var version = mobiledoc.version;\n\n switch (version) {\n case _mobiledocTextRendererRenderers02.MOBILEDOC_VERSION:\n case undefined:\n case null:\n return new _mobiledocTextRendererRenderers02['default'](mobiledoc, this.state).render();\n case _mobiledocTextRendererRenderers03.MOBILEDOC_VERSION:\n return new _mobiledocTextRendererRenderers03['default'](mobiledoc, this.state).render();\n default:\n throw new Error('Unexpected Mobiledoc version \"' + version + '\"');\n }\n }\n }]);\n\n return RendererFactory;\n })();\n\n exports['default'] = RendererFactory;\n});","define('mobiledoc-text-renderer/renderers/0-2', ['exports', 'mobiledoc-text-renderer/cards/image', 'mobiledoc-text-renderer/utils/render-type', 'mobiledoc-text-renderer/utils/section-types'], function (exports, _mobiledocTextRendererCardsImage, _mobiledocTextRendererUtilsRenderType, _mobiledocTextRendererUtilsSectionTypes) {\n /**\n * runtime Text renderer\n * renders a mobiledoc to Text\n *\n * input: mobiledoc\n * output: Text (string)\n */\n 'use strict';\n\n var _slicedToArray = (function () { function sliceIterator(arr, i) { var _arr = []; var _n = true; var _d = false; var _e = undefined; try { for (var _i = arr[Symbol.iterator](), _s; !(_n = (_s = _i.next()).done); _n = true) { _arr.push(_s.value); if (i && _arr.length === i) break; } } catch (err) { _d = true; _e = err; } finally { try { if (!_n && _i['return']) _i['return'](); } finally { if (_d) throw _e; } } return _arr; } return function (arr, i) { if (Array.isArray(arr)) { return arr; } else if (Symbol.iterator in Object(arr)) { return sliceIterator(arr, i); } else { throw new TypeError('Invalid attempt to destructure non-iterable instance'); } }; })();\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n var LINE_BREAK = '\\n';\n\n var MOBILEDOC_VERSION = '0.2.0';\n\n exports.MOBILEDOC_VERSION = MOBILEDOC_VERSION;\n function validateVersion(version) {\n if (version !== MOBILEDOC_VERSION) {\n throw new Error('Unexpected Mobiledoc version \"' + version + '\"');\n }\n }\n\n var Renderer = (function () {\n function Renderer(mobiledoc, state) {\n _classCallCheck(this, Renderer);\n\n var cards = state.cards;\n var cardOptions = state.cardOptions;\n var atoms = state.atoms;\n var unknownCardHandler = state.unknownCardHandler;\n var version = mobiledoc.version;\n var sectionData = mobiledoc.sections;\n\n validateVersion(version);\n\n var _sectionData = _slicedToArray(sectionData, 2);\n\n var sections = _sectionData[1];\n\n this.root = [];\n this.sections = sections;\n this.cards = cards;\n this.atoms = atoms;\n this.cardOptions = cardOptions;\n this.unknownCardHandler = unknownCardHandler || this._defaultUnknownCardHandler;\n\n this._teardownCallbacks = [];\n }\n\n _createClass(Renderer, [{\n key: 'render',\n value: function render() {\n var _this = this;\n\n this.sections.forEach(function (section) {\n _this.root.push(_this.renderSection(section));\n });\n\n var result = this.root.join(LINE_BREAK);\n return { result: result, teardown: function teardown() {\n return _this.teardown();\n } };\n }\n }, {\n key: 'teardown',\n value: function teardown() {\n for (var i = 0; i < this._teardownCallbacks.length; i++) {\n this._teardownCallbacks[i]();\n }\n }\n }, {\n key: 'renderSection',\n\n // for the text renderer, a missing card is a no-op\n value: function renderSection(section) {\n var _section = _slicedToArray(section, 1);\n\n var type = _section[0];\n\n switch (type) {\n case _mobiledocTextRendererUtilsSectionTypes.MARKUP_SECTION_TYPE:\n return this.renderMarkupSection(section);\n case _mobiledocTextRendererUtilsSectionTypes.IMAGE_SECTION_TYPE:\n return this.renderImageSection(section);\n case _mobiledocTextRendererUtilsSectionTypes.LIST_SECTION_TYPE:\n return this.renderListSection(section);\n case _mobiledocTextRendererUtilsSectionTypes.CARD_SECTION_TYPE:\n return this.renderCardSection(section);\n default:\n throw new Error('Unimplemented renderer for type ' + type);\n }\n }\n }, {\n key: 'renderImageSection',\n value: function renderImageSection() {\n return '';\n }\n }, {\n key: 'renderListSection',\n value: function renderListSection(_ref) {\n var _this2 = this;\n\n var _ref2 = _slicedToArray(_ref, 3);\n\n var type = _ref2[0];\n var tagName = _ref2[1];\n var items = _ref2[2];\n\n return items.map(function (li) {\n return _this2.renderListItem(li);\n }).join(LINE_BREAK);\n }\n }, {\n key: 'renderListItem',\n value: function renderListItem(markers) {\n return this.renderMarkers(markers);\n }\n }, {\n key: 'findCard',\n value: function findCard(name) {\n for (var i = 0; i < this.cards.length; i++) {\n if (this.cards[i].name === name) {\n return this.cards[i];\n }\n }\n if (name === _mobiledocTextRendererCardsImage['default'].name) {\n return _mobiledocTextRendererCardsImage['default'];\n }\n return this._createUnknownCard(name);\n }\n }, {\n key: '_createUnknownCard',\n value: function _createUnknownCard(name) {\n return {\n name: name,\n type: _mobiledocTextRendererUtilsRenderType['default'],\n render: this.unknownCardHandler\n };\n }\n }, {\n key: 'renderCardSection',\n value: function renderCardSection(_ref3) {\n var _ref32 = _slicedToArray(_ref3, 3);\n\n var type = _ref32[0];\n var name = _ref32[1];\n var payload = _ref32[2];\n\n var card = this.findCard(name);\n\n var cardArg = this._createCardArgument(card, payload);\n var rendered = card.render(cardArg);\n\n this._validateCardRender(rendered, card.name);\n\n return rendered || '';\n }\n }, {\n key: '_validateCardRender',\n value: function _validateCardRender(rendered, cardName) {\n if (!rendered) {\n return;\n }\n\n if (typeof rendered !== 'string') {\n throw new Error('Card \"' + cardName + '\" must render ' + _mobiledocTextRendererUtilsRenderType['default'] + ', but result was ' + typeof rendered + '\"');\n }\n }\n }, {\n key: '_registerTeardownCallback',\n value: function _registerTeardownCallback(callback) {\n this._teardownCallbacks.push(callback);\n }\n }, {\n key: '_createCardArgument',\n value: function _createCardArgument(card) {\n var _this3 = this;\n\n var payload = arguments.length <= 1 || arguments[1] === undefined ? {} : arguments[1];\n\n var env = {\n name: card.name,\n isInEditor: false,\n onTeardown: function onTeardown(callback) {\n return _this3._registerTeardownCallback(callback);\n }\n };\n\n var options = this.cardOptions;\n\n return { env: env, options: options, payload: payload };\n }\n }, {\n key: 'renderMarkupSection',\n value: function renderMarkupSection(_ref4) {\n var _ref42 = _slicedToArray(_ref4, 3);\n\n var type = _ref42[0];\n var tagName = _ref42[1];\n var markers = _ref42[2];\n\n return this.renderMarkers(markers);\n }\n }, {\n key: 'renderMarkers',\n value: function renderMarkers(markers) {\n var str = '';\n markers.forEach(function (m) {\n var _m = _slicedToArray(m, 3);\n\n var text = _m[2];\n\n str += text;\n });\n return str;\n }\n }, {\n key: '_defaultUnknownCardHandler',\n get: function get() {\n return function () {};\n }\n }]);\n\n return Renderer;\n })();\n\n exports['default'] = Renderer;\n});","define('mobiledoc-text-renderer/renderers/0-3', ['exports', 'mobiledoc-text-renderer/cards/image', 'mobiledoc-text-renderer/utils/render-type', 'mobiledoc-text-renderer/utils/section-types', 'mobiledoc-text-renderer/utils/marker-types'], function (exports, _mobiledocTextRendererCardsImage, _mobiledocTextRendererUtilsRenderType, _mobiledocTextRendererUtilsSectionTypes, _mobiledocTextRendererUtilsMarkerTypes) {\n /**\n * runtime Text renderer\n * renders a mobiledoc to Text\n *\n * input: mobiledoc\n * output: Text (string)\n */\n 'use strict';\n\n var _slicedToArray = (function () { function sliceIterator(arr, i) { var _arr = []; var _n = true; var _d = false; var _e = undefined; try { for (var _i = arr[Symbol.iterator](), _s; !(_n = (_s = _i.next()).done); _n = true) { _arr.push(_s.value); if (i && _arr.length === i) break; } } catch (err) { _d = true; _e = err; } finally { try { if (!_n && _i['return']) _i['return'](); } finally { if (_d) throw _e; } } return _arr; } return function (arr, i) { if (Array.isArray(arr)) { return arr; } else if (Symbol.iterator in Object(arr)) { return sliceIterator(arr, i); } else { throw new TypeError('Invalid attempt to destructure non-iterable instance'); } }; })();\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n var LINE_BREAK = '\\n';\n\n var MOBILEDOC_VERSION = '0.3.0';\n\n exports.MOBILEDOC_VERSION = MOBILEDOC_VERSION;\n function validateVersion(version) {\n if (version !== MOBILEDOC_VERSION) {\n throw new Error('Unexpected Mobiledoc version \"' + version + '\"');\n }\n }\n\n var Renderer = (function () {\n function Renderer(mobiledoc, state) {\n _classCallCheck(this, Renderer);\n\n var cards = state.cards;\n var cardOptions = state.cardOptions;\n var atoms = state.atoms;\n var unknownCardHandler = state.unknownCardHandler;\n var unknownAtomHandler = state.unknownAtomHandler;\n var version = mobiledoc.version;\n var sections = mobiledoc.sections;\n var atomTypes = mobiledoc.atoms;\n var cardTypes = mobiledoc.cards;\n\n validateVersion(version);\n\n this.root = [];\n this.sections = sections;\n this.atomTypes = atomTypes;\n this.cardTypes = cardTypes;\n this.cards = cards;\n this.atoms = atoms;\n this.cardOptions = cardOptions;\n this.unknownCardHandler = unknownCardHandler || this._defaultUnknownCardHandler;\n this.unknownAtomHandler = unknownAtomHandler || this._defaultUnknownAtomHandler;\n\n this._teardownCallbacks = [];\n }\n\n _createClass(Renderer, [{\n key: 'render',\n value: function render() {\n var _this = this;\n\n this.sections.forEach(function (section) {\n _this.root.push(_this.renderSection(section));\n });\n\n var result = this.root.join(LINE_BREAK);\n return { result: result, teardown: function teardown() {\n return _this.teardown();\n } };\n }\n }, {\n key: 'teardown',\n value: function teardown() {\n for (var i = 0; i < this._teardownCallbacks.length; i++) {\n this._teardownCallbacks[i]();\n }\n }\n }, {\n key: 'renderSection',\n value: function renderSection(section) {\n var _section = _slicedToArray(section, 1);\n\n var type = _section[0];\n\n switch (type) {\n case _mobiledocTextRendererUtilsSectionTypes.MARKUP_SECTION_TYPE:\n return this.renderMarkupSection(section);\n case _mobiledocTextRendererUtilsSectionTypes.IMAGE_SECTION_TYPE:\n return this.renderImageSection(section);\n case _mobiledocTextRendererUtilsSectionTypes.LIST_SECTION_TYPE:\n return this.renderListSection(section);\n case _mobiledocTextRendererUtilsSectionTypes.CARD_SECTION_TYPE:\n return this.renderCardSection(section);\n default:\n throw new Error('Unimplemented renderer for type ' + type);\n }\n }\n }, {\n key: 'renderImageSection',\n value: function renderImageSection() {\n return '';\n }\n }, {\n key: 'renderListSection',\n value: function renderListSection(_ref) {\n var _this2 = this;\n\n var _ref2 = _slicedToArray(_ref, 3);\n\n var type = _ref2[0];\n var tagName = _ref2[1];\n var items = _ref2[2];\n\n return items.map(function (li) {\n return _this2.renderListItem(li);\n }).join(LINE_BREAK);\n }\n }, {\n key: 'renderListItem',\n value: function renderListItem(markers) {\n return this.renderMarkers(markers);\n }\n }, {\n key: 'findCard',\n value: function findCard(name) {\n for (var i = 0; i < this.cards.length; i++) {\n if (this.cards[i].name === name) {\n return this.cards[i];\n }\n }\n if (name === _mobiledocTextRendererCardsImage['default'].name) {\n return _mobiledocTextRendererCardsImage['default'];\n }\n return this._createUnknownCard(name);\n }\n }, {\n key: '_findCardByIndex',\n value: function _findCardByIndex(index) {\n var cardType = this.cardTypes[index];\n if (!cardType) {\n throw new Error('No card definition found at index ' + index);\n }\n\n var _cardType = _slicedToArray(cardType, 2);\n\n var name = _cardType[0];\n var payload = _cardType[1];\n\n var card = this.findCard(name);\n\n return {\n card: card,\n payload: payload\n };\n }\n }, {\n key: '_createUnknownCard',\n value: function _createUnknownCard(name) {\n return {\n name: name,\n type: _mobiledocTextRendererUtilsRenderType['default'],\n render: this.unknownCardHandler\n };\n }\n }, {\n key: 'renderCardSection',\n value: function renderCardSection(_ref3) {\n var _ref32 = _slicedToArray(_ref3, 2);\n\n var type = _ref32[0];\n var index = _ref32[1];\n\n var _findCardByIndex2 = this._findCardByIndex(index);\n\n var card = _findCardByIndex2.card;\n var payload = _findCardByIndex2.payload;\n\n var cardArg = this._createCardArgument(card, payload);\n var rendered = card.render(cardArg);\n\n this._validateCardRender(rendered, card.name);\n\n return rendered || '';\n }\n }, {\n key: '_validateCardRender',\n value: function _validateCardRender(rendered, cardName) {\n if (!rendered) {\n return;\n }\n\n if (typeof rendered !== 'string') {\n throw new Error('Card \"' + cardName + '\" must render ' + _mobiledocTextRendererUtilsRenderType['default'] + ', but result was ' + typeof rendered + '\"');\n }\n }\n }, {\n key: '_registerTeardownCallback',\n value: function _registerTeardownCallback(callback) {\n this._teardownCallbacks.push(callback);\n }\n }, {\n key: '_createCardArgument',\n value: function _createCardArgument(card) {\n var _this3 = this;\n\n var payload = arguments.length <= 1 || arguments[1] === undefined ? {} : arguments[1];\n\n var env = {\n name: card.name,\n isInEditor: false,\n onTeardown: function onTeardown(callback) {\n return _this3._registerTeardownCallback(callback);\n }\n };\n\n var options = this.cardOptions;\n\n return { env: env, options: options, payload: payload };\n }\n }, {\n key: 'renderMarkupSection',\n value: function renderMarkupSection(_ref4) {\n var _ref42 = _slicedToArray(_ref4, 3);\n\n var type = _ref42[0];\n var tagName = _ref42[1];\n var markers = _ref42[2];\n\n return this.renderMarkers(markers);\n }\n }, {\n key: 'findAtom',\n value: function findAtom(name) {\n for (var i = 0; i < this.atoms.length; i++) {\n if (this.atoms[i].name === name) {\n return this.atoms[i];\n }\n }\n return this._createUnknownAtom(name);\n }\n }, {\n key: '_createUnknownAtom',\n value: function _createUnknownAtom(name) {\n return {\n name: name,\n type: _mobiledocTextRendererUtilsRenderType['default'],\n render: this.unknownAtomHandler\n };\n }\n }, {\n key: '_createAtomArgument',\n value: function _createAtomArgument(atom, value, payload) {\n var _this4 = this;\n\n var env = {\n name: atom.name,\n onTeardown: function onTeardown(callback) {\n return _this4._registerTeardownCallback(callback);\n }\n };\n\n var options = this.cardOptions;\n\n return { env: env, options: options, value: value, payload: payload };\n }\n }, {\n key: '_validateAtomRender',\n value: function _validateAtomRender(rendered, atomName) {\n if (!rendered) {\n return;\n }\n\n if (typeof rendered !== 'string') {\n throw new Error('Atom \"' + atomName + '\" must render ' + _mobiledocTextRendererUtilsRenderType['default'] + ', but result was ' + typeof rendered + '\"');\n }\n }\n }, {\n key: '_findAtomByIndex',\n value: function _findAtomByIndex(index) {\n var atomType = this.atomTypes[index];\n if (!atomType) {\n throw new Error('No atom definition found at index ' + index);\n }\n\n var _atomType = _slicedToArray(atomType, 3);\n\n var name = _atomType[0];\n var value = _atomType[1];\n var payload = _atomType[2];\n\n var atom = this.findAtom(name);\n\n return {\n atom: atom,\n value: value,\n payload: payload\n };\n }\n }, {\n key: '_renderAtom',\n value: function _renderAtom(index) {\n var _findAtomByIndex2 = this._findAtomByIndex(index);\n\n var atom = _findAtomByIndex2.atom;\n var value = _findAtomByIndex2.value;\n var payload = _findAtomByIndex2.payload;\n\n var atomArg = this._createAtomArgument(atom, value, payload);\n var rendered = atom.render(atomArg);\n\n this._validateAtomRender(rendered, atom.name);\n\n return rendered || '';\n }\n }, {\n key: 'renderMarkers',\n value: function renderMarkers(markers) {\n var _this5 = this;\n\n var str = '';\n markers.forEach(function (m) {\n var _m = _slicedToArray(m, 4);\n\n var type = _m[0];\n var value = _m[3];\n\n switch (type) {\n case _mobiledocTextRendererUtilsMarkerTypes.MARKUP_MARKER_TYPE:\n str += value;\n break;\n case _mobiledocTextRendererUtilsMarkerTypes.ATOM_MARKER_TYPE:\n str += _this5._renderAtom(value);\n break;\n default:\n throw new Error('Unknown markup type (' + type + ')');\n }\n });\n return str;\n }\n }, {\n key: '_defaultUnknownCardHandler',\n get: function get() {\n return function () {\n // for the text renderer, a missing card is a no-op\n };\n }\n }, {\n key: '_defaultUnknownAtomHandler',\n get: function get() {\n return function (_ref5) {\n var value = _ref5.value;\n\n return value || '';\n };\n }\n }]);\n\n return Renderer;\n })();\n\n exports['default'] = Renderer;\n});","define(\"mobiledoc-text-renderer/utils/marker-types\", [\"exports\"], function (exports) {\n \"use strict\";\n\n var MARKUP_MARKER_TYPE = 0;\n exports.MARKUP_MARKER_TYPE = MARKUP_MARKER_TYPE;\n var ATOM_MARKER_TYPE = 1;\n exports.ATOM_MARKER_TYPE = ATOM_MARKER_TYPE;\n});","define('mobiledoc-text-renderer/utils/render-type', ['exports'], function (exports) {\n 'use strict';\n\n exports['default'] = 'text';\n});","define(\"mobiledoc-text-renderer/utils/section-types\", [\"exports\"], function (exports) {\n \"use strict\";\n\n var MARKUP_SECTION_TYPE = 1;\n exports.MARKUP_SECTION_TYPE = MARKUP_SECTION_TYPE;\n var IMAGE_SECTION_TYPE = 2;\n exports.IMAGE_SECTION_TYPE = IMAGE_SECTION_TYPE;\n var LIST_SECTION_TYPE = 3;\n exports.LIST_SECTION_TYPE = LIST_SECTION_TYPE;\n var CARD_SECTION_TYPE = 10;\n exports.CARD_SECTION_TYPE = CARD_SECTION_TYPE;\n});"],"names":[],"mappings":"AAAA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACfA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACVA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACvFA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACpUA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACtcA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AC3GA;AACA;AACA;AACA;AACA;AACA;AACA;;ACNA;AACA;AACA;AACA;;ACHA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACVA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AChCA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AChBA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AC/JA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AClKA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACpvCA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACxVA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACvMA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACxLA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACn2CA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACnWA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACtIA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACjDA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACzFA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AC5FA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACnFA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACvBA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACrWA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACjLA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACxFA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACzHA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AC3IA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AC/EA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACzCA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AC7EA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AC1DA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AC9GA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AC/JA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACvDA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACpEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACvMA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACjRA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACxIA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AC1GA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACpBA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AC1TA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACnCA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AC3MA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AC7RA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACnBA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AC/TA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACzGA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AC9nBA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACjHA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AC9IA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACnBA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACpMA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACPA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACVA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACRA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AC3CA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACXA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AC7OA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AChjBA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACvNA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACpBA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AC3HA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AC7CA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACxEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AClDA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AC/RA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AC3CA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACZA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACjRA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AC9EA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACnHA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACxBA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AClBA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACnBA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AC/KA;AACA;AACA;AACA;AACA;AACA;;ACLA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AChMA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AChDA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AC/BA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACfA;AACA;AACA;AACA;;ACHA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AChEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AChFA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACPA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACVA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACvFA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACvOA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACxWA;AACA;AACA;AACA;AACA;AACA;AACA;;ACNA;AACA;AACA;AACA;;ACHA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;","file":"mobiledoc-kit.js"} \ No newline at end of file +{"version":3,"sources":["mobiledoc-dom-renderer/cards/image.js","mobiledoc-dom-renderer/index.js","mobiledoc-dom-renderer/renderer-factory.js","mobiledoc-dom-renderer/renderers/0-2.js","mobiledoc-dom-renderer/renderers/0-3.js","mobiledoc-dom-renderer/utils/array-utils.js","mobiledoc-dom-renderer/utils/dom.js","mobiledoc-dom-renderer/utils/marker-types.js","mobiledoc-dom-renderer/utils/render-type.js","mobiledoc-dom-renderer/utils/render-utils.js","mobiledoc-dom-renderer/utils/sanitization-utils.js","mobiledoc-dom-renderer/utils/section-types.js","mobiledoc-dom-renderer/utils/tag-names.js","mobiledoc-kit/cards/image.js","mobiledoc-kit/editor/edit-history.js","mobiledoc-kit/editor/edit-state.js","mobiledoc-kit/editor/editor.js","mobiledoc-kit/editor/event-manager.js","mobiledoc-kit/editor/key-commands.js","mobiledoc-kit/editor/mutation-handler.js","mobiledoc-kit/editor/post.js","mobiledoc-kit/editor/post/post-inserter.js","mobiledoc-kit/editor/selection-change-observer.js","mobiledoc-kit/editor/selection-manager.js","mobiledoc-kit/editor/text-input-handler.js","mobiledoc-kit/editor/text-input-handlers.js","mobiledoc-kit/editor/ui.js","mobiledoc-kit/index.js","mobiledoc-kit/models/_markerable.js","mobiledoc-kit/models/_section.js","mobiledoc-kit/models/atom-node.js","mobiledoc-kit/models/atom.js","mobiledoc-kit/models/card-node.js","mobiledoc-kit/models/card.js","mobiledoc-kit/models/image.js","mobiledoc-kit/models/lifecycle-callbacks.js","mobiledoc-kit/models/list-item.js","mobiledoc-kit/models/list-section.js","mobiledoc-kit/models/marker.js","mobiledoc-kit/models/markup-section.js","mobiledoc-kit/models/markup.js","mobiledoc-kit/models/post-node-builder.js","mobiledoc-kit/models/post.js","mobiledoc-kit/models/render-node.js","mobiledoc-kit/models/render-tree.js","mobiledoc-kit/models/types.js","mobiledoc-kit/parsers/dom.js","mobiledoc-kit/parsers/html.js","mobiledoc-kit/parsers/mobiledoc/0-2.js","mobiledoc-kit/parsers/mobiledoc/0-3-1.js","mobiledoc-kit/parsers/mobiledoc/0-3.js","mobiledoc-kit/parsers/mobiledoc/index.js","mobiledoc-kit/parsers/section.js","mobiledoc-kit/parsers/text.js","mobiledoc-kit/renderers/editor-dom.js","mobiledoc-kit/renderers/mobiledoc/0-2.js","mobiledoc-kit/renderers/mobiledoc/0-3-1.js","mobiledoc-kit/renderers/mobiledoc/0-3.js","mobiledoc-kit/renderers/mobiledoc/index.js","mobiledoc-kit/utils/array-utils.js","mobiledoc-kit/utils/assert.js","mobiledoc-kit/utils/browser.js","mobiledoc-kit/utils/characters.js","mobiledoc-kit/utils/compiler.js","mobiledoc-kit/utils/copy.js","mobiledoc-kit/utils/cursor.js","mobiledoc-kit/utils/cursor/position.js","mobiledoc-kit/utils/cursor/range.js","mobiledoc-kit/utils/deprecate.js","mobiledoc-kit/utils/dom-utils.js","mobiledoc-kit/utils/element-map.js","mobiledoc-kit/utils/element-utils.js","mobiledoc-kit/utils/environment.js","mobiledoc-kit/utils/fixed-queue.js","mobiledoc-kit/utils/key.js","mobiledoc-kit/utils/keycodes.js","mobiledoc-kit/utils/linked-item.js","mobiledoc-kit/utils/linked-list.js","mobiledoc-kit/utils/log-manager.js","mobiledoc-kit/utils/markuperable.js","mobiledoc-kit/utils/merge.js","mobiledoc-kit/utils/mixin.js","mobiledoc-kit/utils/mobiledoc-error.js","mobiledoc-kit/utils/parse-utils.js","mobiledoc-kit/utils/placeholder-image-src.js","mobiledoc-kit/utils/selection-utils.js","mobiledoc-kit/utils/set.js","mobiledoc-kit/utils/string-utils.js","mobiledoc-kit/utils/to-range.js","mobiledoc-kit/version.js","mobiledoc-kit/views/tooltip.js","mobiledoc-kit/views/view.js","mobiledoc-text-renderer/cards/image.js","mobiledoc-text-renderer/index.js","mobiledoc-text-renderer/renderer-factory.js","mobiledoc-text-renderer/renderers/0-2.js","mobiledoc-text-renderer/renderers/0-3.js","mobiledoc-text-renderer/utils/marker-types.js","mobiledoc-text-renderer/utils/render-type.js","mobiledoc-text-renderer/utils/section-types.js"],"sourcesContent":["define('mobiledoc-dom-renderer/cards/image', ['exports', 'mobiledoc-dom-renderer/utils/render-type'], function (exports, _mobiledocDomRendererUtilsRenderType) {\n 'use strict';\n\n exports['default'] = {\n name: 'image',\n type: _mobiledocDomRendererUtilsRenderType['default'],\n render: function render(_ref) {\n var payload = _ref.payload;\n var dom = _ref.env.dom;\n\n var img = dom.createElement('img');\n img.src = payload.src;\n return img;\n }\n };\n});","define('mobiledoc-dom-renderer', ['exports', 'mobiledoc-dom-renderer/renderer-factory', 'mobiledoc-dom-renderer/utils/render-type'], function (exports, _mobiledocDomRendererRendererFactory, _mobiledocDomRendererUtilsRenderType) {\n 'use strict';\n\n exports.registerGlobal = registerGlobal;\n exports.RENDER_TYPE = _mobiledocDomRendererUtilsRenderType['default'];\n\n function registerGlobal(window) {\n window.MobiledocDOMRenderer = _mobiledocDomRendererRendererFactory['default'];\n }\n\n exports['default'] = _mobiledocDomRendererRendererFactory['default'];\n});","define('mobiledoc-dom-renderer/renderer-factory', ['exports', 'mobiledoc-dom-renderer/renderers/0-2', 'mobiledoc-dom-renderer/renderers/0-3', 'mobiledoc-dom-renderer/utils/render-type'], function (exports, _mobiledocDomRendererRenderers02, _mobiledocDomRendererRenderers03, _mobiledocDomRendererUtilsRenderType) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n /**\n * runtime DOM renderer\n * renders a mobiledoc to DOM\n *\n * input: mobiledoc\n * output: DOM\n */\n\n function validateCards(cards) {\n if (!Array.isArray(cards)) {\n throw new Error('`cards` must be passed as an array');\n }\n for (var i = 0; i < cards.length; i++) {\n var card = cards[i];\n if (card.type !== _mobiledocDomRendererUtilsRenderType['default']) {\n throw new Error('Card \"' + card.name + '\" must be of type \"' + _mobiledocDomRendererUtilsRenderType['default'] + '\", was \"' + card.type + '\"');\n }\n if (!card.render) {\n throw new Error('Card \"' + card.name + '\" must define `render`');\n }\n }\n }\n\n function validateAtoms(atoms) {\n if (!Array.isArray(atoms)) {\n throw new Error('`atoms` must be passed as an array');\n }\n for (var i = 0; i < atoms.length; i++) {\n var atom = atoms[i];\n if (atom.type !== _mobiledocDomRendererUtilsRenderType['default']) {\n throw new Error('Atom \"' + atom.name + '\" must be type \"' + _mobiledocDomRendererUtilsRenderType['default'] + '\", was \"' + atom.type + '\"');\n }\n if (!atom.render) {\n throw new Error('Atom \"' + atom.name + '\" must define `render`');\n }\n }\n }\n\n var RendererFactory = (function () {\n function RendererFactory() {\n var _ref = arguments.length <= 0 || arguments[0] === undefined ? {} : arguments[0];\n\n var _ref$cards = _ref.cards;\n var cards = _ref$cards === undefined ? [] : _ref$cards;\n var _ref$atoms = _ref.atoms;\n var atoms = _ref$atoms === undefined ? [] : _ref$atoms;\n var _ref$cardOptions = _ref.cardOptions;\n var cardOptions = _ref$cardOptions === undefined ? {} : _ref$cardOptions;\n var unknownCardHandler = _ref.unknownCardHandler;\n var unknownAtomHandler = _ref.unknownAtomHandler;\n var _ref$markupElementRenderer = _ref.markupElementRenderer;\n var markupElementRenderer = _ref$markupElementRenderer === undefined ? {} : _ref$markupElementRenderer;\n var _ref$sectionElementRenderer = _ref.sectionElementRenderer;\n var sectionElementRenderer = _ref$sectionElementRenderer === undefined ? {} : _ref$sectionElementRenderer;\n var dom = _ref.dom;\n var _ref$markupSanitizer = _ref.markupSanitizer;\n var markupSanitizer = _ref$markupSanitizer === undefined ? null : _ref$markupSanitizer;\n\n _classCallCheck(this, RendererFactory);\n\n validateCards(cards);\n validateAtoms(atoms);\n\n if (!dom) {\n if (typeof window === 'undefined') {\n throw new Error('A `dom` option must be provided to the renderer when running without window.document');\n }\n dom = window.document;\n }\n\n this.options = {\n cards: cards,\n atoms: atoms,\n cardOptions: cardOptions,\n unknownCardHandler: unknownCardHandler,\n unknownAtomHandler: unknownAtomHandler,\n markupElementRenderer: markupElementRenderer,\n sectionElementRenderer: sectionElementRenderer,\n dom: dom,\n markupSanitizer: markupSanitizer\n };\n }\n\n _createClass(RendererFactory, [{\n key: 'render',\n value: function render(mobiledoc) {\n var version = mobiledoc.version;\n\n switch (version) {\n case _mobiledocDomRendererRenderers02.MOBILEDOC_VERSION:\n case undefined:\n case null:\n return new _mobiledocDomRendererRenderers02['default'](mobiledoc, this.options).render();\n case _mobiledocDomRendererRenderers03.MOBILEDOC_VERSION_0_3_0:\n case _mobiledocDomRendererRenderers03.MOBILEDOC_VERSION_0_3_1:\n return new _mobiledocDomRendererRenderers03['default'](mobiledoc, this.options).render();\n default:\n throw new Error('Unexpected Mobiledoc version \"' + version + '\"');\n }\n }\n }]);\n\n return RendererFactory;\n })();\n\n exports['default'] = RendererFactory;\n});","define('mobiledoc-dom-renderer/renderers/0-2', ['exports', 'mobiledoc-dom-renderer/utils/dom', 'mobiledoc-dom-renderer/cards/image', 'mobiledoc-dom-renderer/utils/render-type', 'mobiledoc-dom-renderer/utils/section-types', 'mobiledoc-dom-renderer/utils/tag-names', 'mobiledoc-dom-renderer/utils/sanitization-utils', 'mobiledoc-dom-renderer/utils/render-utils'], function (exports, _mobiledocDomRendererUtilsDom, _mobiledocDomRendererCardsImage, _mobiledocDomRendererUtilsRenderType, _mobiledocDomRendererUtilsSectionTypes, _mobiledocDomRendererUtilsTagNames, _mobiledocDomRendererUtilsSanitizationUtils, _mobiledocDomRendererUtilsRenderUtils) {\n 'use strict';\n\n var _slicedToArray = (function () { function sliceIterator(arr, i) { var _arr = []; var _n = true; var _d = false; var _e = undefined; try { for (var _i = arr[Symbol.iterator](), _s; !(_n = (_s = _i.next()).done); _n = true) { _arr.push(_s.value); if (i && _arr.length === i) break; } } catch (err) { _d = true; _e = err; } finally { try { if (!_n && _i['return']) _i['return'](); } finally { if (_d) throw _e; } } return _arr; } return function (arr, i) { if (Array.isArray(arr)) { return arr; } else if (Symbol.iterator in Object(arr)) { return sliceIterator(arr, i); } else { throw new TypeError('Invalid attempt to destructure non-iterable instance'); } }; })();\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n var MOBILEDOC_VERSION = '0.2.0';\n\n exports.MOBILEDOC_VERSION = MOBILEDOC_VERSION;\n var IMAGE_SECTION_TAG_NAME = 'img';\n\n function validateVersion(version) {\n if (version !== MOBILEDOC_VERSION) {\n throw new Error('Unexpected Mobiledoc version \"' + version + '\"');\n }\n }\n\n var Renderer = (function () {\n function Renderer(mobiledoc, options) {\n var _this = this;\n\n _classCallCheck(this, Renderer);\n\n var cards = options.cards;\n var cardOptions = options.cardOptions;\n var unknownCardHandler = options.unknownCardHandler;\n var markupElementRenderer = options.markupElementRenderer;\n var sectionElementRenderer = options.sectionElementRenderer;\n var dom = options.dom;\n var version = mobiledoc.version;\n var sectionData = mobiledoc.sections;\n\n validateVersion(version);\n\n var _sectionData = _slicedToArray(sectionData, 2);\n\n var markerTypes = _sectionData[0];\n var sections = _sectionData[1];\n\n this.dom = dom;\n this.root = dom.createDocumentFragment();\n this.markerTypes = markerTypes;\n this.sections = sections;\n this.cards = cards;\n this.cardOptions = cardOptions;\n this.unknownCardHandler = unknownCardHandler || this._defaultUnknownCardHandler;\n\n this.sectionElementRenderer = {\n '__default__': _mobiledocDomRendererUtilsRenderUtils.defaultSectionElementRenderer\n };\n Object.keys(sectionElementRenderer).forEach(function (key) {\n _this.sectionElementRenderer[key.toLowerCase()] = sectionElementRenderer[key];\n });\n\n this.markupElementRenderer = {\n '__default__': _mobiledocDomRendererUtilsRenderUtils.defaultMarkupElementRenderer\n };\n Object.keys(markupElementRenderer).forEach(function (key) {\n _this.markupElementRenderer[key.toLowerCase()] = markupElementRenderer[key];\n });\n\n this._renderCallbacks = [];\n this._teardownCallbacks = [];\n this._renderedChildNodes = [];\n }\n\n _createClass(Renderer, [{\n key: 'render',\n value: function render() {\n var _this2 = this;\n\n this.sections.forEach(function (section) {\n var rendered = _this2.renderSection(section);\n if (rendered) {\n _this2.root.appendChild(rendered);\n }\n });\n for (var i = 0; i < this._renderCallbacks.length; i++) {\n this._renderCallbacks[i]();\n }\n // maintain a reference to child nodes so they can be cleaned up later by teardown\n this._renderedChildNodes = [];\n var node = this.root.firstChild;\n while (node) {\n this._renderedChildNodes.push(node);\n node = node.nextSibling;\n }\n return { result: this.root, teardown: function teardown() {\n return _this2.teardown();\n } };\n }\n }, {\n key: 'teardown',\n value: function teardown() {\n for (var i = 0; i < this._teardownCallbacks.length; i++) {\n this._teardownCallbacks[i]();\n }\n for (var i = 0; i < this._renderedChildNodes.length; i++) {\n var node = this._renderedChildNodes[i];\n if (node.parentNode) {\n node.parentNode.removeChild(node);\n }\n }\n }\n }, {\n key: 'renderSection',\n value: function renderSection(section) {\n var _section = _slicedToArray(section, 1);\n\n var type = _section[0];\n\n switch (type) {\n case _mobiledocDomRendererUtilsSectionTypes.MARKUP_SECTION_TYPE:\n return this.renderMarkupSection(section);\n case _mobiledocDomRendererUtilsSectionTypes.IMAGE_SECTION_TYPE:\n return this.renderImageSection(section);\n case _mobiledocDomRendererUtilsSectionTypes.LIST_SECTION_TYPE:\n return this.renderListSection(section);\n case _mobiledocDomRendererUtilsSectionTypes.CARD_SECTION_TYPE:\n return this.renderCardSection(section);\n default:\n throw new Error('Cannot render mobiledoc section of type \"' + type + '\"');\n }\n }\n }, {\n key: 'renderMarkersOnElement',\n value: function renderMarkersOnElement(element, markers) {\n var elements = [element];\n var currentElement = element;\n\n var pushElement = function pushElement(openedElement) {\n currentElement.appendChild(openedElement);\n elements.push(openedElement);\n currentElement = openedElement;\n };\n\n for (var i = 0, l = markers.length; i < l; i++) {\n var marker = markers[i];\n\n var _marker = _slicedToArray(marker, 3);\n\n var openTypes = _marker[0];\n var closeCount = _marker[1];\n var text = _marker[2];\n\n for (var j = 0, m = openTypes.length; j < m; j++) {\n var markerType = this.markerTypes[openTypes[j]];\n\n var _markerType = _slicedToArray(markerType, 2);\n\n var tagName = _markerType[0];\n var _markerType$1 = _markerType[1];\n var attrs = _markerType$1 === undefined ? [] : _markerType$1;\n\n if ((0, _mobiledocDomRendererUtilsTagNames.isValidMarkerType)(tagName)) {\n pushElement(this.renderMarkupElement(tagName, attrs));\n } else {\n closeCount--;\n }\n }\n\n currentElement.appendChild((0, _mobiledocDomRendererUtilsDom.createTextNode)(this.dom, text));\n\n for (var j = 0, m = closeCount; j < m; j++) {\n elements.pop();\n currentElement = elements[elements.length - 1];\n }\n }\n }\n\n /**\n * @param attrs Array\n */\n }, {\n key: 'renderMarkupElement',\n value: function renderMarkupElement(tagName, attrs) {\n tagName = tagName.toLowerCase();\n attrs = (0, _mobiledocDomRendererUtilsSanitizationUtils.reduceAttributes)(attrs);\n\n var renderer = this.markupElementRendererFor(tagName);\n return renderer(tagName, this.dom, attrs);\n }\n }, {\n key: 'markupElementRendererFor',\n value: function markupElementRendererFor(tagName) {\n return this.markupElementRenderer[tagName] || this.markupElementRenderer.__default__;\n }\n }, {\n key: 'renderListItem',\n value: function renderListItem(markers) {\n var element = this.dom.createElement('li');\n this.renderMarkersOnElement(element, markers);\n return element;\n }\n }, {\n key: 'renderListSection',\n value: function renderListSection(_ref) {\n var _this3 = this;\n\n var _ref2 = _slicedToArray(_ref, 3);\n\n var type = _ref2[0];\n var tagName = _ref2[1];\n var listItems = _ref2[2];\n\n if (!(0, _mobiledocDomRendererUtilsTagNames.isValidSectionTagName)(tagName, _mobiledocDomRendererUtilsSectionTypes.LIST_SECTION_TYPE)) {\n return;\n }\n var element = this.dom.createElement(tagName);\n listItems.forEach(function (li) {\n element.appendChild(_this3.renderListItem(li));\n });\n return element;\n }\n }, {\n key: 'renderImageSection',\n value: function renderImageSection(_ref3) {\n var _ref32 = _slicedToArray(_ref3, 2);\n\n var type = _ref32[0];\n var src = _ref32[1];\n\n var element = this.dom.createElement(IMAGE_SECTION_TAG_NAME);\n element.src = src;\n return element;\n }\n }, {\n key: 'findCard',\n value: function findCard(name) {\n for (var i = 0; i < this.cards.length; i++) {\n if (this.cards[i].name === name) {\n return this.cards[i];\n }\n }\n if (name === _mobiledocDomRendererCardsImage['default'].name) {\n return _mobiledocDomRendererCardsImage['default'];\n }\n return this._createUnknownCard(name);\n }\n }, {\n key: '_createUnknownCard',\n value: function _createUnknownCard(name) {\n return {\n name: name,\n type: _mobiledocDomRendererUtilsRenderType['default'],\n render: this.unknownCardHandler\n };\n }\n }, {\n key: '_createCardArgument',\n value: function _createCardArgument(card) {\n var _this4 = this;\n\n var payload = arguments.length <= 1 || arguments[1] === undefined ? {} : arguments[1];\n\n var env = {\n name: card.name,\n isInEditor: false,\n dom: this.dom,\n didRender: function didRender(callback) {\n return _this4._registerRenderCallback(callback);\n },\n onTeardown: function onTeardown(callback) {\n return _this4._registerTeardownCallback(callback);\n }\n };\n\n var options = this.cardOptions;\n\n return { env: env, options: options, payload: payload };\n }\n }, {\n key: '_registerRenderCallback',\n value: function _registerRenderCallback(callback) {\n this._renderCallbacks.push(callback);\n }\n }, {\n key: '_registerTeardownCallback',\n value: function _registerTeardownCallback(callback) {\n this._teardownCallbacks.push(callback);\n }\n }, {\n key: 'renderCardSection',\n value: function renderCardSection(_ref4) {\n var _ref42 = _slicedToArray(_ref4, 3);\n\n var type = _ref42[0];\n var name = _ref42[1];\n var payload = _ref42[2];\n\n var card = this.findCard(name);\n\n var cardArg = this._createCardArgument(card, payload);\n var rendered = card.render(cardArg);\n\n this._validateCardRender(rendered, card.name);\n\n return rendered;\n }\n }, {\n key: '_validateCardRender',\n value: function _validateCardRender(rendered, cardName) {\n if (!rendered) {\n return;\n }\n\n if (typeof rendered !== 'object') {\n throw new Error('Card \"' + cardName + '\" must render ' + _mobiledocDomRendererUtilsRenderType['default'] + ', but result was \"' + rendered + '\"');\n }\n }\n }, {\n key: 'renderMarkupSection',\n value: function renderMarkupSection(_ref5) {\n var _ref52 = _slicedToArray(_ref5, 3);\n\n var type = _ref52[0];\n var tagName = _ref52[1];\n var markers = _ref52[2];\n\n tagName = tagName.toLowerCase();\n if (!(0, _mobiledocDomRendererUtilsTagNames.isValidSectionTagName)(tagName, _mobiledocDomRendererUtilsSectionTypes.MARKUP_SECTION_TYPE)) {\n return;\n }\n\n var renderer = this.sectionElementRendererFor(tagName);\n var element = renderer(tagName, this.dom);\n\n this.renderMarkersOnElement(element, markers);\n return element;\n }\n }, {\n key: 'sectionElementRendererFor',\n value: function sectionElementRendererFor(tagName) {\n return this.sectionElementRenderer[tagName] || this.sectionElementRenderer.__default__;\n }\n }, {\n key: '_defaultUnknownCardHandler',\n get: function get() {\n return function (_ref6) {\n var name = _ref6.env.name;\n\n throw new Error('Card \"' + name + '\" not found but no unknownCardHandler was registered');\n };\n }\n }]);\n\n return Renderer;\n })();\n\n exports['default'] = Renderer;\n});","define('mobiledoc-dom-renderer/renderers/0-3', ['exports', 'mobiledoc-dom-renderer/utils/dom', 'mobiledoc-dom-renderer/cards/image', 'mobiledoc-dom-renderer/utils/render-type', 'mobiledoc-dom-renderer/utils/section-types', 'mobiledoc-dom-renderer/utils/tag-names', 'mobiledoc-dom-renderer/utils/sanitization-utils', 'mobiledoc-dom-renderer/utils/render-utils', 'mobiledoc-dom-renderer/utils/marker-types'], function (exports, _mobiledocDomRendererUtilsDom, _mobiledocDomRendererCardsImage, _mobiledocDomRendererUtilsRenderType, _mobiledocDomRendererUtilsSectionTypes, _mobiledocDomRendererUtilsTagNames, _mobiledocDomRendererUtilsSanitizationUtils, _mobiledocDomRendererUtilsRenderUtils, _mobiledocDomRendererUtilsMarkerTypes) {\n 'use strict';\n\n var _slicedToArray = (function () { function sliceIterator(arr, i) { var _arr = []; var _n = true; var _d = false; var _e = undefined; try { for (var _i = arr[Symbol.iterator](), _s; !(_n = (_s = _i.next()).done); _n = true) { _arr.push(_s.value); if (i && _arr.length === i) break; } } catch (err) { _d = true; _e = err; } finally { try { if (!_n && _i['return']) _i['return'](); } finally { if (_d) throw _e; } } return _arr; } return function (arr, i) { if (Array.isArray(arr)) { return arr; } else if (Symbol.iterator in Object(arr)) { return sliceIterator(arr, i); } else { throw new TypeError('Invalid attempt to destructure non-iterable instance'); } }; })();\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n var MOBILEDOC_VERSION_0_3_0 = '0.3.0';\n exports.MOBILEDOC_VERSION_0_3_0 = MOBILEDOC_VERSION_0_3_0;\n var MOBILEDOC_VERSION_0_3_1 = '0.3.1';\n exports.MOBILEDOC_VERSION_0_3_1 = MOBILEDOC_VERSION_0_3_1;\n var MOBILEDOC_VERSION = MOBILEDOC_VERSION_0_3_0;\n\n exports.MOBILEDOC_VERSION = MOBILEDOC_VERSION;\n var IMAGE_SECTION_TAG_NAME = 'img';\n\n function validateVersion(version) {\n switch (version) {\n case MOBILEDOC_VERSION_0_3_0:\n case MOBILEDOC_VERSION_0_3_1:\n return;\n default:\n throw new Error('Unexpected Mobiledoc version \"' + version + '\"');\n }\n }\n\n var Renderer = (function () {\n function Renderer(mobiledoc, state) {\n var _this = this;\n\n _classCallCheck(this, Renderer);\n\n var cards = state.cards;\n var cardOptions = state.cardOptions;\n var atoms = state.atoms;\n var unknownCardHandler = state.unknownCardHandler;\n var unknownAtomHandler = state.unknownAtomHandler;\n var markupElementRenderer = state.markupElementRenderer;\n var sectionElementRenderer = state.sectionElementRenderer;\n var dom = state.dom;\n var version = mobiledoc.version;\n var sections = mobiledoc.sections;\n var atomTypes = mobiledoc.atoms;\n var cardTypes = mobiledoc.cards;\n var markerTypes = mobiledoc.markups;\n\n validateVersion(version);\n\n this.dom = dom;\n this.root = this.dom.createDocumentFragment();\n this.sections = sections;\n this.atomTypes = atomTypes;\n this.cardTypes = cardTypes;\n this.markerTypes = markerTypes;\n this.cards = cards;\n this.atoms = atoms;\n this.cardOptions = cardOptions;\n this.unknownCardHandler = unknownCardHandler || this._defaultUnknownCardHandler;\n this.unknownAtomHandler = unknownAtomHandler || this._defaultUnknownAtomHandler;\n\n this.sectionElementRenderer = {\n '__default__': _mobiledocDomRendererUtilsRenderUtils.defaultSectionElementRenderer\n };\n Object.keys(sectionElementRenderer).forEach(function (key) {\n _this.sectionElementRenderer[key.toLowerCase()] = sectionElementRenderer[key];\n });\n\n this.markupElementRenderer = {\n '__default__': _mobiledocDomRendererUtilsRenderUtils.defaultMarkupElementRenderer\n };\n Object.keys(markupElementRenderer).forEach(function (key) {\n _this.markupElementRenderer[key.toLowerCase()] = markupElementRenderer[key];\n });\n\n this._renderCallbacks = [];\n this._teardownCallbacks = [];\n }\n\n _createClass(Renderer, [{\n key: 'render',\n value: function render() {\n var _this2 = this;\n\n this.sections.forEach(function (section) {\n var rendered = _this2.renderSection(section);\n if (rendered) {\n _this2.root.appendChild(rendered);\n }\n });\n for (var i = 0; i < this._renderCallbacks.length; i++) {\n this._renderCallbacks[i]();\n }\n // maintain a reference to child nodes so they can be cleaned up later by teardown\n this._renderedChildNodes = Array.prototype.slice.call(this.root.childNodes);\n return { result: this.root, teardown: function teardown() {\n return _this2.teardown();\n } };\n }\n }, {\n key: 'teardown',\n value: function teardown() {\n for (var i = 0; i < this._teardownCallbacks.length; i++) {\n this._teardownCallbacks[i]();\n }\n for (var i = 0; i < this._renderedChildNodes.length; i++) {\n var node = this._renderedChildNodes[i];\n if (node.parentNode) {\n node.parentNode.removeChild(node);\n }\n }\n }\n }, {\n key: 'renderSection',\n value: function renderSection(section) {\n var _section = _slicedToArray(section, 1);\n\n var type = _section[0];\n\n switch (type) {\n case _mobiledocDomRendererUtilsSectionTypes.MARKUP_SECTION_TYPE:\n return this.renderMarkupSection(section);\n case _mobiledocDomRendererUtilsSectionTypes.IMAGE_SECTION_TYPE:\n return this.renderImageSection(section);\n case _mobiledocDomRendererUtilsSectionTypes.LIST_SECTION_TYPE:\n return this.renderListSection(section);\n case _mobiledocDomRendererUtilsSectionTypes.CARD_SECTION_TYPE:\n return this.renderCardSection(section);\n default:\n throw new Error('Cannot render mobiledoc section of type \"' + type + '\"');\n }\n }\n }, {\n key: 'renderMarkersOnElement',\n value: function renderMarkersOnElement(element, markers) {\n var elements = [element];\n var currentElement = element;\n\n var pushElement = function pushElement(openedElement) {\n currentElement.appendChild(openedElement);\n elements.push(openedElement);\n currentElement = openedElement;\n };\n\n for (var i = 0, l = markers.length; i < l; i++) {\n var marker = markers[i];\n\n var _marker = _slicedToArray(marker, 4);\n\n var type = _marker[0];\n var openTypes = _marker[1];\n var closeCount = _marker[2];\n var value = _marker[3];\n\n for (var j = 0, m = openTypes.length; j < m; j++) {\n var markerType = this.markerTypes[openTypes[j]];\n\n var _markerType = _slicedToArray(markerType, 2);\n\n var tagName = _markerType[0];\n var _markerType$1 = _markerType[1];\n var attrs = _markerType$1 === undefined ? [] : _markerType$1;\n\n if ((0, _mobiledocDomRendererUtilsTagNames.isValidMarkerType)(tagName)) {\n pushElement(this.renderMarkupElement(tagName, attrs));\n } else {\n closeCount--;\n }\n }\n\n switch (type) {\n case _mobiledocDomRendererUtilsMarkerTypes.MARKUP_MARKER_TYPE:\n currentElement.appendChild((0, _mobiledocDomRendererUtilsDom.createTextNode)(this.dom, value));\n break;\n case _mobiledocDomRendererUtilsMarkerTypes.ATOM_MARKER_TYPE:\n currentElement.appendChild(this._renderAtom(value));\n break;\n default:\n throw new Error('Unknown markup type (' + type + ')');\n }\n\n for (var j = 0, m = closeCount; j < m; j++) {\n elements.pop();\n currentElement = elements[elements.length - 1];\n }\n }\n }\n\n /**\n * @param attrs Array\n */\n }, {\n key: 'renderMarkupElement',\n value: function renderMarkupElement(tagName, attrs) {\n tagName = tagName.toLowerCase();\n attrs = (0, _mobiledocDomRendererUtilsSanitizationUtils.reduceAttributes)(attrs);\n\n var renderer = this.markupElementRendererFor(tagName);\n return renderer(tagName, this.dom, attrs);\n }\n }, {\n key: 'markupElementRendererFor',\n value: function markupElementRendererFor(tagName) {\n return this.markupElementRenderer[tagName] || this.markupElementRenderer.__default__;\n }\n }, {\n key: 'renderListItem',\n value: function renderListItem(markers) {\n var element = this.dom.createElement('li');\n this.renderMarkersOnElement(element, markers);\n return element;\n }\n }, {\n key: 'renderListSection',\n value: function renderListSection(_ref) {\n var _this3 = this;\n\n var _ref2 = _slicedToArray(_ref, 3);\n\n var type = _ref2[0];\n var tagName = _ref2[1];\n var listItems = _ref2[2];\n\n if (!(0, _mobiledocDomRendererUtilsTagNames.isValidSectionTagName)(tagName, _mobiledocDomRendererUtilsSectionTypes.LIST_SECTION_TYPE)) {\n return;\n }\n var element = this.dom.createElement(tagName);\n listItems.forEach(function (li) {\n element.appendChild(_this3.renderListItem(li));\n });\n return element;\n }\n }, {\n key: 'renderImageSection',\n value: function renderImageSection(_ref3) {\n var _ref32 = _slicedToArray(_ref3, 2);\n\n var type = _ref32[0];\n var src = _ref32[1];\n\n var element = this.dom.createElement(IMAGE_SECTION_TAG_NAME);\n element.src = src;\n return element;\n }\n }, {\n key: 'findCard',\n value: function findCard(name) {\n for (var i = 0; i < this.cards.length; i++) {\n if (this.cards[i].name === name) {\n return this.cards[i];\n }\n }\n if (name === _mobiledocDomRendererCardsImage['default'].name) {\n return _mobiledocDomRendererCardsImage['default'];\n }\n return this._createUnknownCard(name);\n }\n }, {\n key: '_findCardByIndex',\n value: function _findCardByIndex(index) {\n var cardType = this.cardTypes[index];\n if (!cardType) {\n throw new Error('No card definition found at index ' + index);\n }\n\n var _cardType = _slicedToArray(cardType, 2);\n\n var name = _cardType[0];\n var payload = _cardType[1];\n\n var card = this.findCard(name);\n\n return {\n card: card,\n payload: payload\n };\n }\n }, {\n key: '_createUnknownCard',\n value: function _createUnknownCard(name) {\n return {\n name: name,\n type: _mobiledocDomRendererUtilsRenderType['default'],\n render: this.unknownCardHandler\n };\n }\n }, {\n key: '_createCardArgument',\n value: function _createCardArgument(card) {\n var _this4 = this;\n\n var payload = arguments.length <= 1 || arguments[1] === undefined ? {} : arguments[1];\n\n var env = {\n name: card.name,\n isInEditor: false,\n dom: this.dom,\n didRender: function didRender(callback) {\n return _this4._registerRenderCallback(callback);\n },\n onTeardown: function onTeardown(callback) {\n return _this4._registerTeardownCallback(callback);\n }\n };\n\n var options = this.cardOptions;\n\n return { env: env, options: options, payload: payload };\n }\n }, {\n key: '_registerTeardownCallback',\n value: function _registerTeardownCallback(callback) {\n this._teardownCallbacks.push(callback);\n }\n }, {\n key: '_registerRenderCallback',\n value: function _registerRenderCallback(callback) {\n this._renderCallbacks.push(callback);\n }\n }, {\n key: 'renderCardSection',\n value: function renderCardSection(_ref4) {\n var _ref42 = _slicedToArray(_ref4, 2);\n\n var type = _ref42[0];\n var index = _ref42[1];\n\n var _findCardByIndex2 = this._findCardByIndex(index);\n\n var card = _findCardByIndex2.card;\n var payload = _findCardByIndex2.payload;\n\n var cardArg = this._createCardArgument(card, payload);\n var rendered = card.render(cardArg);\n\n this._validateCardRender(rendered, card.name);\n\n return rendered;\n }\n }, {\n key: '_validateCardRender',\n value: function _validateCardRender(rendered, cardName) {\n if (!rendered) {\n return;\n }\n\n if (typeof rendered !== 'object') {\n throw new Error('Card \"' + cardName + '\" must render ' + _mobiledocDomRendererUtilsRenderType['default'] + ', but result was \"' + rendered + '\"');\n }\n }\n }, {\n key: 'findAtom',\n value: function findAtom(name) {\n for (var i = 0; i < this.atoms.length; i++) {\n if (this.atoms[i].name === name) {\n return this.atoms[i];\n }\n }\n return this._createUnknownAtom(name);\n }\n }, {\n key: '_createUnknownAtom',\n value: function _createUnknownAtom(name) {\n return {\n name: name,\n type: _mobiledocDomRendererUtilsRenderType['default'],\n render: this.unknownAtomHandler\n };\n }\n }, {\n key: '_createAtomArgument',\n value: function _createAtomArgument(atom, value, payload) {\n var _this5 = this;\n\n var env = {\n name: atom.name,\n isInEditor: false,\n dom: this.dom,\n onTeardown: function onTeardown(callback) {\n return _this5._registerTeardownCallback(callback);\n }\n };\n\n var options = this.cardOptions;\n\n return { env: env, options: options, value: value, payload: payload };\n }\n }, {\n key: '_validateAtomRender',\n value: function _validateAtomRender(rendered, atomName) {\n if (!rendered) {\n return;\n }\n\n if (typeof rendered !== 'object') {\n throw new Error('Atom \"' + atomName + '\" must render ' + _mobiledocDomRendererUtilsRenderType['default'] + ', but result was \"' + rendered + '\"');\n }\n }\n }, {\n key: '_findAtomByIndex',\n value: function _findAtomByIndex(index) {\n var atomType = this.atomTypes[index];\n if (!atomType) {\n throw new Error('No atom definition found at index ' + index);\n }\n\n var _atomType = _slicedToArray(atomType, 3);\n\n var name = _atomType[0];\n var value = _atomType[1];\n var payload = _atomType[2];\n\n var atom = this.findAtom(name);\n\n return {\n atom: atom,\n value: value,\n payload: payload\n };\n }\n }, {\n key: '_renderAtom',\n value: function _renderAtom(index) {\n var _findAtomByIndex2 = this._findAtomByIndex(index);\n\n var atom = _findAtomByIndex2.atom;\n var value = _findAtomByIndex2.value;\n var payload = _findAtomByIndex2.payload;\n\n var atomArg = this._createAtomArgument(atom, value, payload);\n var rendered = atom.render(atomArg);\n\n this._validateAtomRender(rendered, atom.name);\n\n return rendered || (0, _mobiledocDomRendererUtilsDom.createTextNode)(this.dom, '');\n }\n }, {\n key: 'renderMarkupSection',\n value: function renderMarkupSection(_ref5) {\n var _ref52 = _slicedToArray(_ref5, 3);\n\n var type = _ref52[0];\n var tagName = _ref52[1];\n var markers = _ref52[2];\n\n tagName = tagName.toLowerCase();\n if (!(0, _mobiledocDomRendererUtilsTagNames.isValidSectionTagName)(tagName, _mobiledocDomRendererUtilsSectionTypes.MARKUP_SECTION_TYPE)) {\n return;\n }\n\n var renderer = this.sectionElementRendererFor(tagName);\n var element = renderer(tagName, this.dom);\n\n this.renderMarkersOnElement(element, markers);\n return element;\n }\n }, {\n key: 'sectionElementRendererFor',\n value: function sectionElementRendererFor(tagName) {\n return this.sectionElementRenderer[tagName] || this.sectionElementRenderer.__default__;\n }\n }, {\n key: '_defaultUnknownCardHandler',\n get: function get() {\n return function (_ref6) {\n var name = _ref6.env.name;\n\n throw new Error('Card \"' + name + '\" not found but no unknownCardHandler was registered');\n };\n }\n }, {\n key: '_defaultUnknownAtomHandler',\n get: function get() {\n return function (_ref7) {\n var name = _ref7.env.name;\n\n throw new Error('Atom \"' + name + '\" not found but no unknownAtomHandler was registered');\n };\n }\n }]);\n\n return Renderer;\n })();\n\n exports['default'] = Renderer;\n});","define(\"mobiledoc-dom-renderer/utils/array-utils\", [\"exports\"], function (exports) {\n \"use strict\";\n\n exports.includes = includes;\n\n function includes(array, detectValue) {\n for (var i = 0; i < array.length; i++) {\n var value = array[i];\n if (value === detectValue) {\n return true;\n }\n }\n return false;\n }\n});","define('mobiledoc-dom-renderer/utils/dom', ['exports'], function (exports) {\n 'use strict';\n\n exports.createTextNode = createTextNode;\n exports.normalizeTagName = normalizeTagName;\n function addHTMLSpaces(text) {\n var nbsp = ' ';\n return text.replace(/ /g, ' ' + nbsp);\n }\n\n function createTextNode(dom, text) {\n return dom.createTextNode(addHTMLSpaces(text));\n }\n\n function normalizeTagName(tagName) {\n return tagName.toLowerCase();\n }\n});","define(\"mobiledoc-dom-renderer/utils/marker-types\", [\"exports\"], function (exports) {\n \"use strict\";\n\n var MARKUP_MARKER_TYPE = 0;\n exports.MARKUP_MARKER_TYPE = MARKUP_MARKER_TYPE;\n var ATOM_MARKER_TYPE = 1;\n exports.ATOM_MARKER_TYPE = ATOM_MARKER_TYPE;\n});","define('mobiledoc-dom-renderer/utils/render-type', ['exports'], function (exports) {\n 'use strict';\n\n exports['default'] = 'dom';\n});","define('mobiledoc-dom-renderer/utils/render-utils', ['exports', 'mobiledoc-dom-renderer/utils/tag-names', 'mobiledoc-dom-renderer/utils/sanitization-utils'], function (exports, _mobiledocDomRendererUtilsTagNames, _mobiledocDomRendererUtilsSanitizationUtils) {\n 'use strict';\n\n exports.defaultSectionElementRenderer = defaultSectionElementRenderer;\n exports.defaultMarkupElementRenderer = defaultMarkupElementRenderer;\n\n function defaultSectionElementRenderer(tagName, dom) {\n var element = undefined;\n if ((0, _mobiledocDomRendererUtilsTagNames.isMarkupSectionElementName)(tagName)) {\n element = dom.createElement(tagName);\n } else {\n element = dom.createElement('div');\n element.setAttribute('class', tagName);\n }\n\n return element;\n }\n\n function sanitizeAttribute(tagName, attrName, attrValue) {\n if (tagName === 'a' && attrName === 'href') {\n return (0, _mobiledocDomRendererUtilsSanitizationUtils.sanitizeHref)(attrValue);\n } else {\n return attrValue;\n }\n }\n\n function defaultMarkupElementRenderer(tagName, dom, attrsObj) {\n var element = dom.createElement(tagName);\n Object.keys(attrsObj).forEach(function (attrName) {\n var attrValue = attrsObj[attrName];\n attrValue = sanitizeAttribute(tagName, attrName, attrValue);\n element.setAttribute(attrName, attrValue);\n });\n return element;\n }\n});","define('mobiledoc-dom-renderer/utils/sanitization-utils', ['exports', 'mobiledoc-dom-renderer/utils/array-utils'], function (exports, _mobiledocDomRendererUtilsArrayUtils) {\n 'use strict';\n\n exports.sanitizeHref = sanitizeHref;\n exports.reduceAttributes = reduceAttributes;\n\n var PROTOCOL_REGEXP = /^([a-z0-9.+-]+:)/i;\n\n var badProtocols = ['javascript:', // jshint ignore:line\n 'vbscript:' // jshint ignore:line\n ];\n\n function getProtocol(url) {\n var matches = url && url.match(PROTOCOL_REGEXP);\n var protocol = matches && matches[0] || ':';\n return protocol;\n }\n\n function sanitizeHref(url) {\n var protocol = getProtocol(url);\n if ((0, _mobiledocDomRendererUtilsArrayUtils.includes)(badProtocols, protocol)) {\n return 'unsafe:' + url;\n }\n return url;\n }\n\n /**\n * @param attributes array\n * @return obj with normalized attribute names (lowercased)\n */\n\n function reduceAttributes(attributes) {\n var obj = {};\n for (var i = 0; i < attributes.length; i += 2) {\n var key = attributes[i];\n var val = attributes[i + 1];\n obj[key.toLowerCase()] = val;\n }\n return obj;\n }\n});","define(\"mobiledoc-dom-renderer/utils/section-types\", [\"exports\"], function (exports) {\n \"use strict\";\n\n var MARKUP_SECTION_TYPE = 1;\n exports.MARKUP_SECTION_TYPE = MARKUP_SECTION_TYPE;\n var IMAGE_SECTION_TYPE = 2;\n exports.IMAGE_SECTION_TYPE = IMAGE_SECTION_TYPE;\n var LIST_SECTION_TYPE = 3;\n exports.LIST_SECTION_TYPE = LIST_SECTION_TYPE;\n var CARD_SECTION_TYPE = 10;\n exports.CARD_SECTION_TYPE = CARD_SECTION_TYPE;\n});","define('mobiledoc-dom-renderer/utils/tag-names', ['exports', 'mobiledoc-dom-renderer/utils/section-types', 'mobiledoc-dom-renderer/utils/dom'], function (exports, _mobiledocDomRendererUtilsSectionTypes, _mobiledocDomRendererUtilsDom) {\n 'use strict';\n\n exports.isValidSectionTagName = isValidSectionTagName;\n exports.isMarkupSectionElementName = isMarkupSectionElementName;\n exports.isValidMarkerType = isValidMarkerType;\n\n var MARKUP_SECTION_TAG_NAMES = ['p', 'h1', 'h2', 'h3', 'h4', 'h5', 'h6', 'blockquote', 'pull-quote', 'aside'].map(_mobiledocDomRendererUtilsDom.normalizeTagName);\n\n var MARKUP_SECTION_ELEMENT_NAMES = ['p', 'h1', 'h2', 'h3', 'h4', 'h5', 'h6', 'blockquote', 'aside'].map(_mobiledocDomRendererUtilsDom.normalizeTagName);\n\n var LIST_SECTION_TAG_NAMES = ['ul', 'ol'].map(_mobiledocDomRendererUtilsDom.normalizeTagName);\n\n var MARKUP_TYPES = ['b', 'i', 'strong', 'em', 'a', 'u', 'sub', 'sup', 's', 'code'].map(_mobiledocDomRendererUtilsDom.normalizeTagName);\n\n function contains(array, item) {\n return array.indexOf(item) !== -1;\n }\n\n function isValidSectionTagName(tagName, sectionType) {\n tagName = (0, _mobiledocDomRendererUtilsDom.normalizeTagName)(tagName);\n\n switch (sectionType) {\n case _mobiledocDomRendererUtilsSectionTypes.MARKUP_SECTION_TYPE:\n return contains(MARKUP_SECTION_TAG_NAMES, tagName);\n case _mobiledocDomRendererUtilsSectionTypes.LIST_SECTION_TYPE:\n return contains(LIST_SECTION_TAG_NAMES, tagName);\n default:\n throw new Error('Cannot validate tagName for unknown section type \"' + sectionType + '\"');\n }\n }\n\n function isMarkupSectionElementName(tagName) {\n tagName = (0, _mobiledocDomRendererUtilsDom.normalizeTagName)(tagName);\n return contains(MARKUP_SECTION_ELEMENT_NAMES, tagName);\n }\n\n function isValidMarkerType(type) {\n type = (0, _mobiledocDomRendererUtilsDom.normalizeTagName)(type);\n return contains(MARKUP_TYPES, type);\n }\n});","define('mobiledoc-kit/cards/image', ['exports', 'mobiledoc-kit/utils/placeholder-image-src'], function (exports, _mobiledocKitUtilsPlaceholderImageSrc) {\n 'use strict';\n\n exports['default'] = {\n name: 'image',\n type: 'dom',\n\n render: function render(_ref) {\n var env = _ref.env;\n var options = _ref.options;\n var payload = _ref.payload;\n\n var img = document.createElement('img');\n img.src = payload.src || _mobiledocKitUtilsPlaceholderImageSrc['default'];\n return img;\n }\n };\n});","define('mobiledoc-kit/editor/edit-history', ['exports', 'mobiledoc-kit/parsers/mobiledoc', 'mobiledoc-kit/utils/fixed-queue'], function (exports, _mobiledocKitParsersMobiledoc, _mobiledocKitUtilsFixedQueue) {\n 'use strict';\n\n var _slicedToArray = (function () { function sliceIterator(arr, i) { var _arr = []; var _n = true; var _d = false; var _e = undefined; try { for (var _i = arr[Symbol.iterator](), _s; !(_n = (_s = _i.next()).done); _n = true) { _arr.push(_s.value); if (i && _arr.length === i) break; } } catch (err) { _d = true; _e = err; } finally { try { if (!_n && _i['return']) _i['return'](); } finally { if (_d) throw _e; } } return _arr; } return function (arr, i) { if (Array.isArray(arr)) { return arr; } else if (Symbol.iterator in Object(arr)) { return sliceIterator(arr, i); } else { throw new TypeError('Invalid attempt to destructure non-iterable instance'); } }; })();\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n function findLeafSectionAtIndex(post, index) {\n var section = undefined;\n post.walkAllLeafSections(function (_section, _index) {\n if (index === _index) {\n section = _section;\n }\n });\n return section;\n }\n\n var Snapshot = (function () {\n function Snapshot(takenAt, editor) {\n var editAction = arguments.length <= 2 || arguments[2] === undefined ? null : arguments[2];\n\n _classCallCheck(this, Snapshot);\n\n this.mobiledoc = editor.serialize();\n this.editor = editor;\n this.editAction = editAction;\n this.takenAt = takenAt;\n\n this.snapshotRange();\n }\n\n _createClass(Snapshot, [{\n key: 'snapshotRange',\n value: function snapshotRange() {\n var _editor = this.editor;\n var range = _editor.range;\n var cursor = _editor.cursor;\n\n if (cursor.hasCursor() && !range.isBlank) {\n var head = range.head;\n var tail = range.tail;\n\n this.range = {\n head: [head.leafSectionIndex, head.offset],\n tail: [tail.leafSectionIndex, tail.offset]\n };\n }\n }\n }, {\n key: 'getRange',\n value: function getRange(post) {\n if (this.range) {\n var _range = this.range;\n var head = _range.head;\n var tail = _range.tail;\n var _head = head;\n\n var _head2 = _slicedToArray(_head, 2);\n\n var headLeafSectionIndex = _head2[0];\n var headOffset = _head2[1];\n var _tail = tail;\n\n var _tail2 = _slicedToArray(_tail, 2);\n\n var tailLeafSectionIndex = _tail2[0];\n var tailOffset = _tail2[1];\n\n var headSection = findLeafSectionAtIndex(post, headLeafSectionIndex);\n var tailSection = findLeafSectionAtIndex(post, tailLeafSectionIndex);\n\n head = headSection.toPosition(headOffset);\n tail = tailSection.toPosition(tailOffset);\n\n return head.toRange(tail);\n }\n }\n }, {\n key: 'groupsWith',\n value: function groupsWith(groupingTimeout, editAction, takenAt) {\n return editAction !== null && this.editAction === editAction && this.takenAt + groupingTimeout > takenAt;\n }\n }]);\n\n return Snapshot;\n })();\n\n exports.Snapshot = Snapshot;\n\n var EditHistory = (function () {\n function EditHistory(editor, queueLength, groupingTimeout) {\n _classCallCheck(this, EditHistory);\n\n this.editor = editor;\n this._undoStack = new _mobiledocKitUtilsFixedQueue['default'](queueLength);\n this._redoStack = new _mobiledocKitUtilsFixedQueue['default'](queueLength);\n\n this._pendingSnapshot = null;\n this._groupingTimeout = groupingTimeout;\n }\n\n _createClass(EditHistory, [{\n key: 'snapshot',\n value: function snapshot() {\n // update the current snapshot with the range read from DOM\n if (this._pendingSnapshot) {\n this._pendingSnapshot.snapshotRange();\n }\n }\n }, {\n key: 'storeSnapshot',\n value: function storeSnapshot() {\n var editAction = arguments.length <= 0 || arguments[0] === undefined ? null : arguments[0];\n\n var now = Date.now();\n // store pending snapshot\n var pendingSnapshot = this._pendingSnapshot;\n if (pendingSnapshot) {\n if (!pendingSnapshot.groupsWith(this._groupingTimeout, editAction, now)) {\n this._undoStack.push(pendingSnapshot);\n }\n this._redoStack.clear();\n }\n\n // take new pending snapshot to store next time `storeSnapshot` is called\n this._pendingSnapshot = new Snapshot(now, this.editor, editAction);\n }\n }, {\n key: 'stepBackward',\n value: function stepBackward(postEditor) {\n // Throw away the pending snapshot\n this._pendingSnapshot = null;\n\n var snapshot = this._undoStack.pop();\n if (snapshot) {\n this._redoStack.push(new Snapshot(Date.now(), this.editor));\n this._restoreFromSnapshot(snapshot, postEditor);\n }\n }\n }, {\n key: 'stepForward',\n value: function stepForward(postEditor) {\n var snapshot = this._redoStack.pop();\n if (snapshot) {\n this._undoStack.push(new Snapshot(Date.now(), this.editor));\n this._restoreFromSnapshot(snapshot, postEditor);\n }\n postEditor.cancelSnapshot();\n }\n }, {\n key: '_restoreFromSnapshot',\n value: function _restoreFromSnapshot(snapshot, postEditor) {\n var mobiledoc = snapshot.mobiledoc;\n var editor = this.editor;\n var builder = editor.builder;\n var post = editor.post;\n\n var restoredPost = _mobiledocKitParsersMobiledoc['default'].parse(builder, mobiledoc);\n\n postEditor.removeAllSections();\n postEditor.migrateSectionsFromPost(restoredPost);\n\n // resurrect snapshotted range if it exists\n var newRange = snapshot.getRange(post);\n if (newRange) {\n postEditor.setRange(newRange);\n }\n }\n }]);\n\n return EditHistory;\n })();\n\n exports['default'] = EditHistory;\n});","define('mobiledoc-kit/editor/edit-state', ['exports', 'mobiledoc-kit/utils/array-utils', 'mobiledoc-kit/utils/cursor/range'], function (exports, _mobiledocKitUtilsArrayUtils, _mobiledocKitUtilsCursorRange) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n /**\n * Used by {@link Editor} to manage its current state (cursor, active markups\n * and active sections).\n * @private\n */\n\n var EditState = (function () {\n function EditState(editor) {\n _classCallCheck(this, EditState);\n\n this.editor = editor;\n\n var defaultState = {\n range: _mobiledocKitUtilsCursorRange['default'].blankRange(),\n activeMarkups: [],\n activeSections: [],\n activeSectionTagNames: []\n };\n\n this.prevState = this.state = defaultState;\n }\n\n _createClass(EditState, [{\n key: 'updateRange',\n value: function updateRange(newRange) {\n this.prevState = this.state;\n this.state = this._readState(newRange);\n }\n }, {\n key: 'destroy',\n value: function destroy() {\n this.editor = null;\n this.prevState = this.state = null;\n }\n\n /**\n * @return {Boolean}\n */\n }, {\n key: 'rangeDidChange',\n value: function rangeDidChange() {\n var range = this.state.range;\n var prevRange = this.prevState.range;\n\n return !prevRange.isEqual(range);\n }\n\n /**\n * @return {Boolean} Whether the input mode (active markups or active section tag names)\n * has changed.\n */\n }, {\n key: 'inputModeDidChange',\n value: function inputModeDidChange() {\n var state = this.state;\n var prevState = this.prevState;\n\n return !(0, _mobiledocKitUtilsArrayUtils.isArrayEqual)(state.activeMarkups, prevState.activeMarkups) || !(0, _mobiledocKitUtilsArrayUtils.isArrayEqual)(state.activeSectionTagNames, prevState.activeSectionTagNames);\n }\n\n /**\n * @return {Range}\n */\n }, {\n key: 'toggleMarkupState',\n\n /**\n * Update the editor's markup state. This is used when, e.g.,\n * a user types meta+B when the editor has a cursor but no selected text;\n * in this case the editor needs to track that it has an active \"b\" markup\n * and apply it to the next text the user types.\n */\n value: function toggleMarkupState(markup) {\n if ((0, _mobiledocKitUtilsArrayUtils.contains)(this.activeMarkups, markup)) {\n this._removeActiveMarkup(markup);\n } else {\n this._addActiveMarkup(markup);\n }\n }\n }, {\n key: '_readState',\n value: function _readState(range) {\n var state = {\n range: range,\n activeMarkups: this._readActiveMarkups(range),\n activeSections: this._readActiveSections(range)\n };\n // Section objects are 'live', so to check that they changed, we\n // need to map their tagNames now (and compare to mapped tagNames later).\n // In addition, to catch changes from ul -> ol, we keep track of the\n // un-nested tag names (otherwise we'd only see li -> li change)\n state.activeSectionTagNames = state.activeSections.map(function (s) {\n return s.isNested ? s.parent.tagName : s.tagName;\n });\n return state;\n }\n }, {\n key: '_readActiveSections',\n value: function _readActiveSections(range) {\n var head = range.head;\n var tail = range.tail;\n var post = this.editor.post;\n\n if (range.isBlank) {\n return [];\n } else {\n return post.sections.readRange(head.section, tail.section);\n }\n }\n }, {\n key: '_readActiveMarkups',\n value: function _readActiveMarkups(range) {\n var post = this.editor.post;\n\n return post.markupsInRange(range);\n }\n }, {\n key: '_removeActiveMarkup',\n value: function _removeActiveMarkup(markup) {\n var index = this.state.activeMarkups.indexOf(markup);\n this.state.activeMarkups.splice(index, 1);\n }\n }, {\n key: '_addActiveMarkup',\n value: function _addActiveMarkup(markup) {\n this.state.activeMarkups.push(markup);\n }\n }, {\n key: 'range',\n get: function get() {\n return this.state.range;\n }\n\n /**\n * @return {Section[]}\n */\n }, {\n key: 'activeSections',\n get: function get() {\n return this.state.activeSections;\n }\n\n /**\n * @return {Markup[]}\n */\n }, {\n key: 'activeMarkups',\n get: function get() {\n return this.state.activeMarkups;\n }\n }]);\n\n return EditState;\n })();\n\n exports['default'] = EditState;\n});","define('mobiledoc-kit/editor/editor', ['exports', 'mobiledoc-kit/views/tooltip', 'mobiledoc-kit/editor/post', 'mobiledoc-kit/cards/image', 'mobiledoc-kit/utils/key', 'mobiledoc-kit/parsers/mobiledoc', 'mobiledoc-kit/parsers/html', 'mobiledoc-kit/parsers/dom', 'mobiledoc-kit/renderers/editor-dom', 'mobiledoc-kit/models/render-tree', 'mobiledoc-kit/renderers/mobiledoc', 'mobiledoc-kit/utils/merge', 'mobiledoc-kit/utils/dom-utils', 'mobiledoc-kit/utils/array-utils', 'mobiledoc-kit/utils/element-utils', 'mobiledoc-kit/utils/cursor', 'mobiledoc-kit/utils/cursor/range', 'mobiledoc-kit/utils/cursor/position', 'mobiledoc-kit/utils/environment', 'mobiledoc-kit/models/post-node-builder', 'mobiledoc-kit/editor/text-input-handlers', 'mobiledoc-kit/editor/key-commands', 'mobiledoc-kit/models/card', 'mobiledoc-kit/utils/assert', 'mobiledoc-kit/editor/mutation-handler', 'mobiledoc-kit/editor/edit-history', 'mobiledoc-kit/editor/event-manager', 'mobiledoc-kit/editor/edit-state', 'mobiledoc-dom-renderer', 'mobiledoc-text-renderer', 'mobiledoc-kit/models/lifecycle-callbacks', 'mobiledoc-kit/utils/log-manager', 'mobiledoc-kit/utils/to-range', 'mobiledoc-kit/utils/mobiledoc-error'], function (exports, _mobiledocKitViewsTooltip, _mobiledocKitEditorPost, _mobiledocKitCardsImage, _mobiledocKitUtilsKey, _mobiledocKitParsersMobiledoc, _mobiledocKitParsersHtml, _mobiledocKitParsersDom, _mobiledocKitRenderersEditorDom, _mobiledocKitModelsRenderTree, _mobiledocKitRenderersMobiledoc, _mobiledocKitUtilsMerge, _mobiledocKitUtilsDomUtils, _mobiledocKitUtilsArrayUtils, _mobiledocKitUtilsElementUtils, _mobiledocKitUtilsCursor, _mobiledocKitUtilsCursorRange, _mobiledocKitUtilsCursorPosition, _mobiledocKitUtilsEnvironment, _mobiledocKitModelsPostNodeBuilder, _mobiledocKitEditorTextInputHandlers, _mobiledocKitEditorKeyCommands, _mobiledocKitModelsCard, _mobiledocKitUtilsAssert, _mobiledocKitEditorMutationHandler, _mobiledocKitEditorEditHistory, _mobiledocKitEditorEventManager, _mobiledocKitEditorEditState, _mobiledocDomRenderer, _mobiledocTextRenderer, _mobiledocKitModelsLifecycleCallbacks, _mobiledocKitUtilsLogManager, _mobiledocKitUtilsToRange, _mobiledocKitUtilsMobiledocError) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n // This export may later be deprecated, but re-export it from the renderer here\n // for consumers that may depend on it.\n Object.defineProperty(exports, 'EDITOR_ELEMENT_CLASS_NAME', {\n enumerable: true,\n get: function get() {\n return _mobiledocKitRenderersEditorDom.EDITOR_ELEMENT_CLASS_NAME;\n }\n });\n\n var defaults = {\n placeholder: 'Write here...',\n spellcheck: true,\n autofocus: true,\n undoDepth: 5,\n undoBlockTimeout: 5000, // ms for an undo event\n cards: [],\n atoms: [],\n cardOptions: {},\n unknownCardHandler: function unknownCardHandler(_ref) {\n var env = _ref.env;\n\n throw new _mobiledocKitUtilsMobiledocError['default']('Unknown card encountered: ' + env.name);\n },\n unknownAtomHandler: function unknownAtomHandler(_ref2) {\n var env = _ref2.env;\n\n throw new _mobiledocKitUtilsMobiledocError['default']('Unknown atom encountered: ' + env.name);\n },\n mobiledoc: null,\n html: null\n };\n\n var CALLBACK_QUEUES = {\n DID_UPDATE: 'didUpdate',\n WILL_RENDER: 'willRender',\n DID_RENDER: 'didRender',\n WILL_DELETE: 'willDelete',\n DID_DELETE: 'didDelete',\n WILL_HANDLE_NEWLINE: 'willHandleNewline',\n CURSOR_DID_CHANGE: 'cursorDidChange',\n DID_REPARSE: 'didReparse',\n POST_DID_CHANGE: 'postDidChange',\n INPUT_MODE_DID_CHANGE: 'inputModeDidChange'\n };\n\n /**\n * The Editor is a core component of mobiledoc-kit. After instantiating\n * an editor, use {@link Editor#render} to display the editor on the web page.\n *\n * An editor uses a {@link Post} internally to represent the displayed document.\n * The post can be serialized as mobiledoc using {@link Editor#serialize}. Mobiledoc\n * is the transportable \"over-the-wire\" format (JSON) that is suited for persisting\n * and sharing between editors and renderers (for display, e.g.), whereas the Post\n * model is better suited for programmatic editing.\n *\n * The editor will call registered callbacks for certain state changes. These are:\n * * {@link Editor#cursorDidChange} -- The cursor position or selection changed.\n * * {@link Editor#postDidChange} -- The contents of the post changed due to user input or\n * programmatic editing. This hook can be used with {@link Editor#serialize}\n * to auto-save a post as it is being edited.\n * * {@link Editor#inputModeDidChange} -- The active section(s) or markup(s) at the current cursor\n * position or selection have changed. This hook can be used with\n * {@link Editor#activeMarkups} and {@link Editor#activeSections} to implement\n * a custom toolbar.\n * * {@link Editor#onTextInput} -- Register callbacks when the user enters text\n * that matches a given string or regex.\n */\n\n var Editor = (function () {\n /**\n * @param {Object} [options]\n * @param {Object} [options.mobiledoc] The mobiledoc to load into the editor.\n * Supersedes `options.html`.\n * @param {String|DOM} [options.html] The html (as a string or DOM fragment)\n * to parse and load into the editor.\n * Will be ignored if `options.mobiledoc` is also passed.\n * @param {Array} [options.parserPlugins=[]]\n * @param {Array} [options.cards=[]] The cards that the editor may render.\n * @param {Array} [options.atoms=[]] The atoms that the editor may render.\n * @param {Function} [options.unknownCardHandler] Invoked by the editor's renderer\n * whenever it encounters an unknown card.\n * @param {Function} [options.unknownAtomHandler] Invoked by the editor's renderer\n * whenever it encounters an unknown atom.\n * @param {String} [options.placeholder] Default text to show before user starts typing.\n * @param {Boolean} [options.spellcheck=true] Whether to enable spellcheck\n * @param {Boolean} [options.autofocus=true] Whether to focus the editor when it is first rendered.\n * @param {number} [options.undoDepth=5] How many undo levels will be available.\n * Set to 0 to disable undo/redo functionality.\n * @return {Editor}\n * @public\n */\n\n function Editor() {\n var _this = this;\n\n var options = arguments.length <= 0 || arguments[0] === undefined ? {} : arguments[0];\n\n _classCallCheck(this, Editor);\n\n (0, _mobiledocKitUtilsAssert['default'])('editor create accepts an options object. For legacy usage passing an element for the first argument, consider the `html` option for loading DOM or HTML posts. For other cases call `editor.render(domNode)` after editor creation', options && !options.nodeType);\n this._views = [];\n this.isEditable = null;\n this._parserPlugins = options.parserPlugins || [];\n\n // FIXME: This should merge onto this.options\n (0, _mobiledocKitUtilsMerge.mergeWithOptions)(this, defaults, options);\n this.cards.push(_mobiledocKitCardsImage['default']);\n\n _mobiledocKitEditorKeyCommands.DEFAULT_KEY_COMMANDS.forEach(function (kc) {\n return _this.registerKeyCommand(kc);\n });\n\n this._logManager = new _mobiledocKitUtilsLogManager['default']();\n this._parser = new _mobiledocKitParsersDom['default'](this.builder);\n var cards = this.cards;\n var atoms = this.atoms;\n var unknownCardHandler = this.unknownCardHandler;\n var unknownAtomHandler = this.unknownAtomHandler;\n var cardOptions = this.cardOptions;\n\n this._renderer = new _mobiledocKitRenderersEditorDom['default'](this, cards, atoms, unknownCardHandler, unknownAtomHandler, cardOptions);\n\n this.post = this.loadPost();\n this._renderTree = new _mobiledocKitModelsRenderTree['default'](this.post);\n\n this._editHistory = new _mobiledocKitEditorEditHistory['default'](this, this.undoDepth, this.undoBlockTimeout);\n this._eventManager = new _mobiledocKitEditorEventManager['default'](this);\n this._mutationHandler = new _mobiledocKitEditorMutationHandler['default'](this);\n this._editState = new _mobiledocKitEditorEditState['default'](this);\n this._callbacks = new _mobiledocKitModelsLifecycleCallbacks['default']((0, _mobiledocKitUtilsArrayUtils.values)(CALLBACK_QUEUES));\n\n _mobiledocKitEditorTextInputHandlers.DEFAULT_TEXT_INPUT_HANDLERS.forEach(function (handler) {\n return _this.onTextInput(handler);\n });\n\n this.hasRendered = false;\n }\n\n /**\n * Turns on verbose logging for the editor.\n * @param {Array} [logTypes=[]] If present, only the given log types will be logged.\n * @public\n */\n\n _createClass(Editor, [{\n key: 'enableLogging',\n value: function enableLogging() {\n var logTypes = arguments.length <= 0 || arguments[0] === undefined ? [] : arguments[0];\n\n if (logTypes.length === 0) {\n this._logManager.enableAll();\n } else {\n this._logManager.enableTypes(logTypes);\n }\n }\n\n /**\n * Disable all logging\n * @public\n */\n }, {\n key: 'disableLogging',\n value: function disableLogging() {\n this._logManager.disable();\n }\n\n /**\n * @private\n */\n }, {\n key: 'loggerFor',\n value: function loggerFor(type) {\n return this._logManager['for'](type);\n }\n\n /**\n * The editor's instance of a post node builder.\n * @type {PostNodeBuilder}\n */\n }, {\n key: 'loadPost',\n value: function loadPost() {\n var mobiledoc = this.mobiledoc;\n var html = this.html;\n\n if (mobiledoc) {\n return _mobiledocKitParsersMobiledoc['default'].parse(this.builder, mobiledoc);\n } else if (html) {\n if (typeof html === 'string') {\n var options = { plugins: this._parserPlugins };\n return new _mobiledocKitParsersHtml['default'](this.builder, options).parse(this.html);\n } else {\n var dom = html;\n return this._parser.parse(dom);\n }\n } else {\n return this.builder.createPost();\n }\n }\n }, {\n key: 'rerender',\n value: function rerender() {\n var _this2 = this;\n\n var postRenderNode = this.post.renderNode;\n\n // if we haven't rendered this post's renderNode before, mark it dirty\n if (!postRenderNode.element) {\n (0, _mobiledocKitUtilsAssert['default'])('Must call `render` before `rerender` can be called', this.hasRendered);\n postRenderNode.element = this.element;\n postRenderNode.markDirty();\n }\n\n this.runCallbacks(CALLBACK_QUEUES.WILL_RENDER);\n this._mutationHandler.suspendObservation(function () {\n _this2._renderer.render(_this2._renderTree);\n });\n this.runCallbacks(CALLBACK_QUEUES.DID_RENDER);\n }\n\n /**\n * @param {Element} element The DOM element to render into.\n * Its contents will be replaced by the editor's rendered post.\n * @public\n */\n }, {\n key: 'render',\n value: function render(element) {\n (0, _mobiledocKitUtilsAssert['default'])('Cannot render an editor twice. Use `rerender` to update the ' + 'rendering of an existing editor instance.', !this.hasRendered);\n\n element.spellcheck = this.spellcheck;\n\n (0, _mobiledocKitUtilsDomUtils.clearChildNodes)(element);\n\n this.element = element;\n\n if (this.isEditable === null) {\n this.enableEditing();\n }\n\n this._addTooltip();\n\n // A call to `run` will trigger the didUpdatePostCallbacks hooks with a\n // postEditor.\n this.run(function () {});\n\n // Only set `hasRendered` to true after calling `run` to ensure that\n // no cursorDidChange or other callbacks get fired before the editor is\n // done rendering\n this.hasRendered = true;\n this.rerender();\n\n this._mutationHandler.init();\n this._eventManager.init();\n\n if (this.autofocus) {\n this.selectRange(this.post.headPosition());\n }\n }\n }, {\n key: '_addTooltip',\n value: function _addTooltip() {\n this.addView(new _mobiledocKitViewsTooltip['default']({\n rootElement: this.element,\n showForTag: 'a'\n }));\n }\n }, {\n key: 'registerKeyCommand',\n\n /**\n * @param {Object} keyCommand The key command to register. It must specify a\n * modifier key (meta, ctrl, etc), a string representing the ascii key, and\n * a `run` method that will be passed the editor instance when the key command\n * is invoked\n * @public\n */\n value: function registerKeyCommand(rawKeyCommand) {\n var keyCommand = (0, _mobiledocKitEditorKeyCommands.buildKeyCommand)(rawKeyCommand);\n (0, _mobiledocKitUtilsAssert['default'])('Key Command is not valid', (0, _mobiledocKitEditorKeyCommands.validateKeyCommand)(keyCommand));\n this.keyCommands.unshift(keyCommand);\n }\n\n /**\n * @param {String} name If the keyCommand event has a name attribute it can be removed.\n * @public\n */\n }, {\n key: 'unregisterKeyCommands',\n value: function unregisterKeyCommands(name) {\n for (var i = this.keyCommands.length - 1; i > -1; i--) {\n var keyCommand = this.keyCommands[i];\n\n if (keyCommand.name === name) {\n this.keyCommands.splice(i, 1);\n }\n }\n }\n\n /**\n * Convenience for {@link PostEditor#deleteAtPosition}. Deletes and puts the\n * cursor in the new position.\n * @public\n */\n }, {\n key: 'deleteAtPosition',\n value: function deleteAtPosition(position, direction, _ref3) {\n var unit = _ref3.unit;\n\n this.run(function (postEditor) {\n var nextPosition = postEditor.deleteAtPosition(position, direction, { unit: unit });\n postEditor.setRange(nextPosition);\n });\n }\n\n /**\n * Convenience for {@link PostEditor#deleteRange}. Deletes and puts the\n * cursor in the new position.\n * @param {Range} range\n * @public\n */\n }, {\n key: 'deleteRange',\n value: function deleteRange(range) {\n this.run(function (postEditor) {\n var nextPosition = postEditor.deleteRange(range);\n postEditor.setRange(nextPosition);\n });\n }\n\n /**\n * @private\n */\n }, {\n key: 'performDelete',\n value: function performDelete() {\n var _ref4 = arguments.length <= 0 || arguments[0] === undefined ? { direction: _mobiledocKitUtilsKey.DIRECTION.BACKWARD, unit: 'char' } : arguments[0];\n\n var direction = _ref4.direction;\n var unit = _ref4.unit;\n var range = this.range;\n\n this.runCallbacks(CALLBACK_QUEUES.WILL_DELETE, [range, direction, unit]);\n if (range.isCollapsed) {\n this.deleteAtPosition(range.head, direction, { unit: unit });\n } else {\n this.deleteRange(range);\n }\n this.runCallbacks(CALLBACK_QUEUES.DID_DELETE, [range, direction, unit]);\n }\n }, {\n key: 'handleNewline',\n value: function handleNewline(event) {\n var _this3 = this;\n\n if (!this.hasCursor()) {\n return;\n }\n\n event.preventDefault();\n\n var range = this.range;\n\n this.run(function (postEditor) {\n var cursorSection = undefined;\n if (!range.isCollapsed) {\n var nextPosition = postEditor.deleteRange(range);\n cursorSection = nextPosition.section;\n if (cursorSection && cursorSection.isBlank) {\n postEditor.setRange(cursorSection.headPosition());\n return;\n }\n }\n\n // Above logic might delete redundant range, so callback must run after it.\n var defaultPrevented = false;\n var event = { preventDefault: function preventDefault() {\n defaultPrevented = true;\n } };\n _this3.runCallbacks(CALLBACK_QUEUES.WILL_HANDLE_NEWLINE, [event]);\n if (defaultPrevented) {\n return;\n }\n\n cursorSection = postEditor.splitSection(range.head)[1];\n postEditor.setRange(cursorSection.headPosition());\n });\n }\n\n /**\n * Notify the editor that the post did change, and run associated\n * callbacks.\n * @private\n */\n }, {\n key: '_postDidChange',\n value: function _postDidChange() {\n this.runCallbacks(CALLBACK_QUEUES.POST_DID_CHANGE);\n }\n\n /**\n * Selects the given range or position. If given a collapsed range or a position, this positions the cursor\n * at the range's position. Otherwise a selection is created in the editor\n * surface encompassing the range.\n * @param {Range|Position} range\n */\n }, {\n key: 'selectRange',\n value: function selectRange(range) {\n range = (0, _mobiledocKitUtilsToRange['default'])(range);\n\n this.cursor.selectRange(range);\n this.range = range;\n }\n }, {\n key: '_readRangeFromDOM',\n value: function _readRangeFromDOM() {\n this.range = this.cursor.offsets;\n }\n }, {\n key: 'setPlaceholder',\n value: function setPlaceholder(placeholder) {\n (0, _mobiledocKitUtilsElementUtils.setData)(this.element, 'placeholder', placeholder);\n }\n }, {\n key: '_reparsePost',\n value: function _reparsePost() {\n var post = this._parser.parse(this.element);\n this.run(function (postEditor) {\n postEditor.removeAllSections();\n postEditor.migrateSectionsFromPost(post);\n postEditor.setRange(_mobiledocKitUtilsCursorRange['default'].blankRange());\n });\n\n this.runCallbacks(CALLBACK_QUEUES.DID_REPARSE);\n this._postDidChange();\n }\n }, {\n key: '_reparseSections',\n value: function _reparseSections() {\n var _this4 = this;\n\n var sections = arguments.length <= 0 || arguments[0] === undefined ? [] : arguments[0];\n\n var currentRange = undefined;\n sections.forEach(function (section) {\n _this4._parser.reparseSection(section, _this4._renderTree);\n });\n this._removeDetachedSections();\n\n if (this._renderTree.isDirty) {\n currentRange = this.range;\n }\n\n // force the current snapshot's range to remain the same rather than\n // rereading it from DOM after the new character is applied and the browser\n // updates the cursor position\n var range = this._editHistory._pendingSnapshot.range;\n this.run(function () {\n _this4._editHistory._pendingSnapshot.range = range;\n });\n this.rerender();\n if (currentRange) {\n this.selectRange(currentRange);\n }\n\n this.runCallbacks(CALLBACK_QUEUES.DID_REPARSE);\n this._postDidChange();\n }\n\n // FIXME this should be able to be removed now -- if any sections are detached,\n // it's due to a bug in the code.\n }, {\n key: '_removeDetachedSections',\n value: function _removeDetachedSections() {\n (0, _mobiledocKitUtilsArrayUtils.forEach)((0, _mobiledocKitUtilsArrayUtils.filter)(this.post.sections, function (s) {\n return !s.renderNode.isAttached();\n }), function (s) {\n return s.renderNode.scheduleForRemoval();\n });\n }\n\n /**\n * The sections from the cursor's selection start to the selection end\n * @type {Section[]}\n */\n }, {\n key: 'detectMarkupInRange',\n value: function detectMarkupInRange(range, markupTagName) {\n var markups = this.post.markupsInRange(range);\n return (0, _mobiledocKitUtilsArrayUtils.detect)(markups, function (markup) {\n return markup.hasTag(markupTagName);\n });\n }\n\n /**\n * @type {Markup[]}\n * @public\n */\n }, {\n key: 'hasActiveMarkup',\n\n /**\n * @param {Markup|String} markup A markup instance, or a string (e.g. \"b\")\n * @return {boolean}\n */\n value: function hasActiveMarkup(markup) {\n var matchesFn = undefined;\n if (typeof markup === 'string') {\n (function () {\n var tagName = (0, _mobiledocKitUtilsDomUtils.normalizeTagName)(markup);\n matchesFn = function (m) {\n return m.tagName === tagName;\n };\n })();\n } else {\n matchesFn = function (m) {\n return m === markup;\n };\n }\n\n return !!(0, _mobiledocKitUtilsArrayUtils.detect)(this.activeMarkups, matchesFn);\n }\n\n /**\n * @param {String} version The mobiledoc version to serialize to.\n * @return {Mobiledoc} Serialized mobiledoc\n * @public\n */\n }, {\n key: 'serialize',\n value: function serialize() {\n var version = arguments.length <= 0 || arguments[0] === undefined ? _mobiledocKitRenderersMobiledoc.MOBILEDOC_VERSION : arguments[0];\n\n return this.serializePost(this.post, 'mobiledoc', { version: version });\n }\n\n /**\n * Serialize the editor's post to the requested format.\n * Note that only mobiledoc format is lossless. If cards or atoms are present\n * in the post, the html and text formats will omit them in output because\n * the editor does not have access to the html and text versions of the\n * cards/atoms.\n * @param {string} format The format to serialize ('mobiledoc', 'text', 'html')\n * @return {Object|String} The editor's post, serialized to {format}\n * @public\n */\n }, {\n key: 'serializeTo',\n value: function serializeTo(format) {\n var post = this.post;\n return this.serializePost(post, format);\n }\n\n /**\n * @param {Post}\n * @param {String} format Same as {serializeTo}\n * @param {Object} [options]\n * @param {String} [options.version=MOBILEDOC_VERSION] version to serialize to\n * @return {Object|String}\n * @private\n */\n }, {\n key: 'serializePost',\n value: function serializePost(post, format) {\n var options = arguments.length <= 2 || arguments[2] === undefined ? {} : arguments[2];\n\n var validFormats = ['mobiledoc', 'html', 'text'];\n (0, _mobiledocKitUtilsAssert['default'])('Unrecognized serialization format ' + format, (0, _mobiledocKitUtilsArrayUtils.contains)(validFormats, format));\n\n if (format === 'mobiledoc') {\n var version = options.version || _mobiledocKitRenderersMobiledoc.MOBILEDOC_VERSION;\n return _mobiledocKitRenderersMobiledoc['default'].render(post, version);\n } else {\n var rendered = undefined;\n var mobiledoc = this.serializePost(post, 'mobiledoc');\n var unknownCardHandler = function unknownCardHandler() {};\n var unknownAtomHandler = function unknownAtomHandler() {};\n var rendererOptions = { unknownCardHandler: unknownCardHandler, unknownAtomHandler: unknownAtomHandler };\n\n switch (format) {\n case 'html':\n var result = undefined;\n if (_mobiledocKitUtilsEnvironment['default'].hasDOM()) {\n rendered = new _mobiledocDomRenderer['default'](rendererOptions).render(mobiledoc);\n result = '
' + (0, _mobiledocKitUtilsDomUtils.serializeHTML)(rendered.result) + '
';\n } else {\n // Fallback to text serialization\n result = this.serializePost(post, 'text', options);\n }\n return result;\n case 'text':\n rendered = new _mobiledocTextRenderer['default'](rendererOptions).render(mobiledoc);\n return rendered.result;\n }\n }\n }\n }, {\n key: 'addView',\n value: function addView(view) {\n this._views.push(view);\n }\n }, {\n key: 'removeAllViews',\n value: function removeAllViews() {\n this._views.forEach(function (v) {\n return v.destroy();\n });\n this._views = [];\n }\n\n /**\n * Whether the editor has a cursor (or a selected range).\n * It is possible for the editor to be focused but not have a selection.\n * In this case, key events will fire but the editor will not be able to\n * determine a cursor position, so they will be ignored.\n * @return {boolean}\n * @public\n */\n }, {\n key: 'hasCursor',\n value: function hasCursor() {\n return this.cursor.hasCursor();\n }\n\n /**\n * Tears down the editor's attached event listeners and views.\n * @public\n */\n }, {\n key: 'destroy',\n value: function destroy() {\n this.isDestroyed = true;\n if (this._hasSelection()) {\n this.cursor.clearSelection();\n }\n if (this._hasFocus()) {\n this.element.blur(); // FIXME This doesn't blur the element on IE11\n }\n this._mutationHandler.destroy();\n this._eventManager.destroy();\n this.removeAllViews();\n this._renderer.destroy();\n this._editState.destroy();\n }\n\n /**\n * Keep the user from directly editing the post using the keyboard and mouse.\n * Modification via the programmatic API is still permitted.\n * @see Editor#enableEditing\n * @public\n */\n }, {\n key: 'disableEditing',\n value: function disableEditing() {\n if (this.isEditable === false) {\n return;\n }\n\n this.isEditable = false;\n if (this.hasRendered) {\n this.element.setAttribute('contentEditable', false);\n this.setPlaceholder('');\n this.selectRange(_mobiledocKitUtilsCursorRange['default'].blankRange());\n }\n }\n\n /**\n * Allow the user to directly interact with editing a post via keyboard and mouse input.\n * Editor instances are editable by default. Use this method to re-enable\n * editing after disabling it.\n * @see Editor#disableEditing\n * @public\n */\n }, {\n key: 'enableEditing',\n value: function enableEditing() {\n this.isEditable = true;\n if (this.element) {\n this.element.setAttribute('contentEditable', true);\n this.setPlaceholder(this.placeholder);\n }\n }\n\n /**\n * Change a cardSection into edit mode\n * If called before the card has been rendered, it will be marked so that\n * it is rendered in edit mode when it gets rendered.\n * @param {CardSection} cardSection\n * @public\n */\n }, {\n key: 'editCard',\n value: function editCard(cardSection) {\n this._setCardMode(cardSection, _mobiledocKitModelsCard.CARD_MODES.EDIT);\n }\n\n /**\n * Change a cardSection into display mode\n * If called before the card has been rendered, it will be marked so that\n * it is rendered in display mode when it gets rendered.\n * @param {CardSection} cardSection\n * @return undefined\n * @public\n */\n }, {\n key: 'displayCard',\n value: function displayCard(cardSection) {\n this._setCardMode(cardSection, _mobiledocKitModelsCard.CARD_MODES.DISPLAY);\n }\n\n /**\n * Run a new post editing session. Yields a block with a new {@link PostEditor}\n * instance. This instance can be used to interact with the post abstract.\n * Rendering will be deferred until after the callback is completed.\n *\n * Usage:\n * ```\n * let markerRange = this.range;\n * editor.run((postEditor) => {\n * postEditor.deleteRange(markerRange);\n * // editing surface not updated yet\n * postEditor.schedule(() => {\n * console.log('logs during rerender flush');\n * });\n * // logging not yet flushed\n * });\n * // editing surface now updated.\n * // logging now flushed\n * ```\n *\n * @param {Function} callback Called with an instance of\n * {@link PostEditor} as its argument.\n * @return {Mixed} The return value of `callback`.\n * @public\n */\n }, {\n key: 'run',\n value: function run(callback) {\n var postEditor = new _mobiledocKitEditorPost['default'](this);\n postEditor.begin();\n this._editHistory.snapshot();\n var result = callback(postEditor);\n this.runCallbacks(CALLBACK_QUEUES.DID_UPDATE, [postEditor]);\n postEditor.complete();\n this._readRangeFromDOM();\n\n if (postEditor._shouldCancelSnapshot) {\n this._editHistory._pendingSnapshot = null;\n }\n this._editHistory.storeSnapshot(postEditor.editActionTaken);\n\n return result;\n }\n\n /**\n * @param {Function} callback Called with `postEditor` as its argument.\n * @public\n */\n }, {\n key: 'didUpdatePost',\n value: function didUpdatePost(callback) {\n this.addCallback(CALLBACK_QUEUES.DID_UPDATE, callback);\n }\n\n /**\n * @param {Function} callback Called when the post has changed, either via\n * user input or programmatically. Use with {@link Editor#serialize} to\n * retrieve the post in portable mobiledoc format.\n */\n }, {\n key: 'postDidChange',\n value: function postDidChange(callback) {\n this.addCallback(CALLBACK_QUEUES.POST_DID_CHANGE, callback);\n }\n\n /**\n * Register a handler that will be invoked by the editor after the user enters\n * matching text.\n * @param {Object} inputHandler\n * @param {String} inputHandler.name Required. Used by identifying handlers.\n * @param {String} [inputHandler.text] Required if `match` is not provided\n * @param {RegExp} [inputHandler.match] Required if `text` is not provided\n * @param {Function} inputHandler.run This callback is invoked with the {@link Editor}\n * instance and an array of matches. If `text` was provided,\n * the matches array will equal [`text`], and if a `match`\n * regex was provided the matches array will be the result of\n * `match.exec` on the matching text. The callback is called\n * after the matching text has been inserted.\n * @public\n */\n }, {\n key: 'onTextInput',\n value: function onTextInput(inputHandler) {\n this._eventManager.registerInputHandler(inputHandler);\n }\n\n /**\n * Unregister all text input handlers\n *\n * @public\n */\n }, {\n key: 'unregisterAllTextInputHandlers',\n value: function unregisterAllTextInputHandlers() {\n this._eventManager.unregisterAllTextInputHandlers();\n }\n\n /**\n * Unregister text input handler by name\n * @param {String} name The name of handler to be removed\n *\n * @public\n */\n }, {\n key: 'unregisterTextInputHandler',\n value: function unregisterTextInputHandler(name) {\n this._eventManager.unregisterInputHandler(name);\n }\n\n /**\n * @param {Function} callback Called when the editor's state (active markups or\n * active sections) has changed, either via user input or programmatically\n */\n }, {\n key: 'inputModeDidChange',\n value: function inputModeDidChange(callback) {\n this.addCallback(CALLBACK_QUEUES.INPUT_MODE_DID_CHANGE, callback);\n }\n\n /**\n * @param {Function} callback This callback will be called before the editor\n * is rendered.\n * @public\n */\n }, {\n key: 'willRender',\n value: function willRender(callback) {\n this.addCallback(CALLBACK_QUEUES.WILL_RENDER, callback);\n }\n\n /**\n * @param {Function} callback This callback will be called after the editor\n * is rendered.\n * @public\n */\n }, {\n key: 'didRender',\n value: function didRender(callback) {\n this.addCallback(CALLBACK_QUEUES.DID_RENDER, callback);\n }\n\n /**\n * @param {Function} callback This callback will be called before deleting.\n * @public\n */\n }, {\n key: 'willDelete',\n value: function willDelete(callback) {\n this.addCallback(CALLBACK_QUEUES.WILL_DELETE, callback);\n }\n\n /**\n * @param {Function} callback This callback will be called after deleting.\n * @public\n */\n }, {\n key: 'didDelete',\n value: function didDelete(callback) {\n this.addCallback(CALLBACK_QUEUES.DID_DELETE, callback);\n }\n\n /**\n * @param {Function} callback This callback will be called before handling new line.\n * @public\n */\n }, {\n key: 'willHandleNewline',\n value: function willHandleNewline(callback) {\n this.addCallback(CALLBACK_QUEUES.WILL_HANDLE_NEWLINE, callback);\n }\n\n /**\n * @param {Function} callback This callback will be called every time the cursor\n * position (or selection) changes.\n * @public\n */\n }, {\n key: 'cursorDidChange',\n value: function cursorDidChange(callback) {\n this.addCallback(CALLBACK_QUEUES.CURSOR_DID_CHANGE, callback);\n }\n }, {\n key: '_rangeDidChange',\n value: function _rangeDidChange() {\n if (this.hasRendered) {\n this.runCallbacks(CALLBACK_QUEUES.CURSOR_DID_CHANGE);\n }\n }\n }, {\n key: '_inputModeDidChange',\n value: function _inputModeDidChange() {\n this.runCallbacks(CALLBACK_QUEUES.INPUT_MODE_DID_CHANGE);\n }\n }, {\n key: '_insertEmptyMarkupSectionAtCursor',\n value: function _insertEmptyMarkupSectionAtCursor() {\n var _this5 = this;\n\n this.run(function (postEditor) {\n var section = postEditor.builder.createMarkupSection('p');\n postEditor.insertSectionBefore(_this5.post.sections, section);\n postEditor.setRange(section.toRange());\n });\n }\n\n /**\n * Toggles the given markup at the editor's current {@link Range}.\n * If the range is collapsed this changes the editor's state so that the\n * next characters typed will be affected. If there is text selected\n * (aka a non-collapsed range), the selections' markup will be toggled.\n * If the editor is not focused and has no active range, nothing happens.\n * @param {String} markup E.g. \"b\", \"em\", \"a\"\n * @public\n * @see PostEditor#toggleMarkup\n */\n }, {\n key: 'toggleMarkup',\n value: function toggleMarkup(markup) {\n markup = this.builder.createMarkup(markup);\n var range = this.range;\n\n if (range.isCollapsed) {\n this._editState.toggleMarkupState(markup);\n this._inputModeDidChange();\n\n // when clicking a button to toggle markup, the button can end up being focused,\n // so ensure the editor is focused\n this._ensureFocus();\n } else {\n this.run(function (postEditor) {\n return postEditor.toggleMarkup(markup, range);\n });\n }\n }\n\n // If the editor has a selection but is not focused, focus it\n }, {\n key: '_ensureFocus',\n value: function _ensureFocus() {\n if (this._hasSelection() && !this._hasFocus()) {\n this.focus();\n }\n }\n }, {\n key: 'focus',\n value: function focus() {\n this.element.focus();\n }\n\n /**\n * Whether there is a selection inside the editor's element.\n * It's possible to have a selection but not have focus.\n * @see #_hasFocus\n * @return {Boolean}\n */\n }, {\n key: '_hasSelection',\n value: function _hasSelection() {\n var cursor = this.cursor;\n\n return this.hasRendered && (cursor._hasCollapsedSelection() || cursor._hasSelection());\n }\n\n /**\n * Whether the editor's element is focused\n * It's possible to be focused but have no selection\n * @see #_hasSelection\n * @return {Boolean}\n */\n }, {\n key: '_hasFocus',\n value: function _hasFocus() {\n return document.activeElement === this.element;\n }\n\n /**\n * Toggles the tagName for the current active section(s). This will skip\n * non-markerable sections. E.g. if the editor's range includes a \"P\" MarkupSection\n * and a CardSection, only the MarkupSection will be toggled.\n * @param {String} tagName The new tagname to change to.\n * @public\n * @see PostEditor#toggleSection\n */\n }, {\n key: 'toggleSection',\n value: function toggleSection(tagName) {\n var _this6 = this;\n\n this.run(function (postEditor) {\n return postEditor.toggleSection(tagName, _this6.range);\n });\n }\n\n /**\n * Finds and runs the first matching key command for the event\n *\n * If multiple commands are bound to a key combination, the\n * first matching one is run.\n *\n * If a command returns `false` then the next matching command\n * is run instead.\n *\n * @param {Event} event The keyboard event triggered by the user\n * @return {Boolean} true when a command was successfully run\n * @private\n */\n }, {\n key: 'handleKeyCommand',\n value: function handleKeyCommand(event) {\n var keyCommands = (0, _mobiledocKitEditorKeyCommands.findKeyCommands)(this.keyCommands, event);\n for (var i = 0; i < keyCommands.length; i++) {\n var keyCommand = keyCommands[i];\n if (keyCommand.run(this) !== false) {\n event.preventDefault();\n return true;\n }\n }\n return false;\n }\n\n /**\n * Inserts the text at the current cursor position. If the editor has\n * no current cursor position, nothing will be inserted. If the editor's\n * range is not collapsed, it will be deleted before insertion.\n *\n * @param {String} text\n * @public\n */\n }, {\n key: 'insertText',\n value: function insertText(text) {\n if (!this.hasCursor()) {\n return;\n }\n if (this.post.isBlank) {\n this._insertEmptyMarkupSectionAtCursor();\n }\n var activeMarkups = this.activeMarkups;\n var range = this.range;\n var position = this.range.head;\n\n this.run(function (postEditor) {\n if (!range.isCollapsed) {\n position = postEditor.deleteRange(range);\n }\n\n postEditor.insertTextWithMarkup(position, text, activeMarkups);\n });\n }\n\n /**\n * Inserts an atom at the current cursor position. If the editor has\n * no current cursor position, nothing will be inserted. If the editor's\n * range is not collapsed, it will be deleted before insertion.\n * @param {String} atomName\n * @param {String} [atomText='']\n * @param {Object} [atomPayload={}]\n * @return {Atom} The inserted atom.\n * @public\n */\n }, {\n key: 'insertAtom',\n value: function insertAtom(atomName) {\n var atomText = arguments.length <= 1 || arguments[1] === undefined ? '' : arguments[1];\n var atomPayload = arguments.length <= 2 || arguments[2] === undefined ? {} : arguments[2];\n\n if (!this.hasCursor()) {\n return;\n }\n if (this.post.isBlank) {\n this._insertEmptyMarkupSectionAtCursor();\n }\n\n var atom = undefined;\n var range = this.range;\n\n this.run(function (postEditor) {\n var position = range.head;\n\n atom = postEditor.builder.createAtom(atomName, atomText, atomPayload);\n if (!range.isCollapsed) {\n position = postEditor.deleteRange(range);\n }\n\n postEditor.insertMarkers(position, [atom]);\n });\n return atom;\n }\n\n /**\n * Inserts a card at the section after the current cursor position. If the editor has\n * no current cursor position, nothing will be inserted. If the editor's\n * range is not collapsed, it will be deleted before insertion. If the cursor is in\n * a blank section, it will be replaced with a card section.\n * The editor's cursor will be placed at the end of the inserted card.\n * @param {String} cardName\n * @param {Object} [cardPayload={}]\n * @param {Boolean} [inEditMode=false] Whether the card should be inserted in edit mode.\n * @return {Card} The inserted Card section.\n * @public\n */\n }, {\n key: 'insertCard',\n value: function insertCard(cardName) {\n var _this7 = this;\n\n var cardPayload = arguments.length <= 1 || arguments[1] === undefined ? {} : arguments[1];\n var inEditMode = arguments.length <= 2 || arguments[2] === undefined ? false : arguments[2];\n\n if (!this.hasCursor()) {\n return;\n }\n if (this.post.isBlank) {\n this._insertEmptyMarkupSectionAtCursor();\n }\n\n var card = undefined;\n var range = this.range;\n\n this.run(function (postEditor) {\n var position = range.tail;\n card = postEditor.builder.createCardSection(cardName, cardPayload);\n if (inEditMode) {\n _this7.editCard(card);\n }\n\n if (!range.isCollapsed) {\n position = postEditor.deleteRange(range);\n }\n\n var section = position.section;\n if (section.isNested) {\n section = section.parent;\n }\n\n if (section.isBlank) {\n postEditor.replaceSection(section, card);\n } else {\n var collection = _this7.post.sections;\n postEditor.insertSectionBefore(collection, card, section.next);\n }\n\n // It is important to explicitly set the range to the end of the card.\n // Otherwise it is possible to create an inconsistent state in the\n // browser. For instance, if the user clicked a button that\n // called `editor.insertCard`, the editor surface may retain\n // the selection but lose focus, and the next keystroke by the user\n // will cause an unexpected DOM mutation (which can wipe out the\n // card).\n // See: https://github.com/bustle/mobiledoc-kit/issues/286\n postEditor.setRange(card.tailPosition());\n });\n return card;\n }\n\n /**\n * @param {integer} x x-position in viewport\n * @param {integer} y y-position in viewport\n * @return {Position|null}\n */\n }, {\n key: 'positionAtPoint',\n value: function positionAtPoint(x, y) {\n return _mobiledocKitUtilsCursorPosition['default'].atPoint(x, y, this);\n }\n\n /**\n * @private\n */\n }, {\n key: '_setCardMode',\n value: function _setCardMode(cardSection, mode) {\n var renderNode = cardSection.renderNode;\n if (renderNode && renderNode.isRendered) {\n var cardNode = renderNode.cardNode;\n cardNode[mode]();\n } else {\n cardSection.setInitialMode(mode);\n }\n }\n }, {\n key: 'triggerEvent',\n value: function triggerEvent(context, eventName, event) {\n this._eventManager._trigger(context, eventName, event);\n }\n }, {\n key: 'addCallback',\n value: function addCallback() {\n var _callbacks;\n\n (_callbacks = this._callbacks).addCallback.apply(_callbacks, arguments);\n }\n }, {\n key: 'addCallbackOnce',\n value: function addCallbackOnce() {\n var _callbacks2;\n\n (_callbacks2 = this._callbacks).addCallbackOnce.apply(_callbacks2, arguments);\n }\n }, {\n key: 'runCallbacks',\n value: function runCallbacks() {\n var _callbacks3;\n\n if (this.isDestroyed) {\n // TODO warn that callback attempted after editor was destroyed\n return;\n }\n (_callbacks3 = this._callbacks).runCallbacks.apply(_callbacks3, arguments);\n }\n }, {\n key: 'builder',\n get: function get() {\n if (!this._builder) {\n this._builder = new _mobiledocKitModelsPostNodeBuilder['default']();\n }\n return this._builder;\n }\n }, {\n key: 'keyCommands',\n get: function get() {\n if (!this._keyCommands) {\n this._keyCommands = [];\n }\n return this._keyCommands;\n }\n }, {\n key: 'cursor',\n get: function get() {\n return new _mobiledocKitUtilsCursor['default'](this);\n }\n\n /**\n * Return the current range for the editor (may be cached).\n * @return {Range}\n */\n }, {\n key: 'range',\n get: function get() {\n return this._editState.range;\n },\n set: function set(newRange) {\n this._editState.updateRange(newRange);\n\n if (this._editState.rangeDidChange()) {\n this._rangeDidChange();\n }\n\n if (this._editState.inputModeDidChange()) {\n this._inputModeDidChange();\n }\n }\n }, {\n key: 'activeSections',\n get: function get() {\n return this._editState.activeSections;\n }\n }, {\n key: 'activeSection',\n get: function get() {\n var activeSections = this.activeSections;\n\n return activeSections[activeSections.length - 1];\n }\n }, {\n key: 'activeMarkups',\n get: function get() {\n return this._editState.activeMarkups;\n }\n }]);\n\n return Editor;\n })();\n\n exports['default'] = Editor;\n});","define('mobiledoc-kit/editor/event-manager', ['exports', 'mobiledoc-kit/utils/assert', 'mobiledoc-kit/utils/parse-utils', 'mobiledoc-kit/utils/array-utils', 'mobiledoc-kit/utils/key', 'mobiledoc-kit/editor/text-input-handler', 'mobiledoc-kit/editor/selection-manager', 'mobiledoc-kit/utils/browser'], function (exports, _mobiledocKitUtilsAssert, _mobiledocKitUtilsParseUtils, _mobiledocKitUtilsArrayUtils, _mobiledocKitUtilsKey, _mobiledocKitEditorTextInputHandler, _mobiledocKitEditorSelectionManager, _mobiledocKitUtilsBrowser) {\n 'use strict';\n\n var _slicedToArray = (function () { function sliceIterator(arr, i) { var _arr = []; var _n = true; var _d = false; var _e = undefined; try { for (var _i = arr[Symbol.iterator](), _s; !(_n = (_s = _i.next()).done); _n = true) { _arr.push(_s.value); if (i && _arr.length === i) break; } } catch (err) { _d = true; _e = err; } finally { try { if (!_n && _i['return']) _i['return'](); } finally { if (_d) throw _e; } } return _arr; } return function (arr, i) { if (Array.isArray(arr)) { return arr; } else if (Symbol.iterator in Object(arr)) { return sliceIterator(arr, i); } else { throw new TypeError('Invalid attempt to destructure non-iterable instance'); } }; })();\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n var ELEMENT_EVENT_TYPES = ['keydown', 'keyup', 'cut', 'copy', 'paste', 'keypress', 'drop'];\n\n var EventManager = (function () {\n function EventManager(editor) {\n _classCallCheck(this, EventManager);\n\n this.editor = editor;\n this.logger = editor.loggerFor('event-manager');\n this._textInputHandler = new _mobiledocKitEditorTextInputHandler['default'](editor);\n this._listeners = [];\n this.modifierKeys = {\n shift: false,\n alt: false,\n ctrl: false\n };\n\n this._selectionManager = new _mobiledocKitEditorSelectionManager['default'](this.editor, this.selectionDidChange.bind(this));\n }\n\n _createClass(EventManager, [{\n key: 'init',\n value: function init() {\n var _this = this;\n\n var element = this.editor.element;\n\n (0, _mobiledocKitUtilsAssert['default'])('Cannot init EventManager without element', !!element);\n\n ELEMENT_EVENT_TYPES.forEach(function (type) {\n _this._addListener(element, type);\n });\n\n this._selectionManager.start();\n }\n }, {\n key: 'registerInputHandler',\n value: function registerInputHandler(inputHandler) {\n this._textInputHandler.register(inputHandler);\n }\n }, {\n key: 'unregisterInputHandler',\n value: function unregisterInputHandler(name) {\n this._textInputHandler.unregister(name);\n }\n }, {\n key: 'unregisterAllTextInputHandlers',\n value: function unregisterAllTextInputHandlers() {\n this._textInputHandler.destroy();\n this._textInputHandler = new _mobiledocKitEditorTextInputHandler['default'](this.editor);\n }\n }, {\n key: '_addListener',\n value: function _addListener(context, type) {\n var _this2 = this;\n\n (0, _mobiledocKitUtilsAssert['default'])('Missing listener for ' + type, !!this[type]);\n\n var listener = function listener(event) {\n return _this2._handleEvent(type, event);\n };\n context.addEventListener(type, listener);\n this._listeners.push([context, type, listener]);\n }\n }, {\n key: '_removeListeners',\n value: function _removeListeners() {\n this._listeners.forEach(function (_ref) {\n var _ref2 = _slicedToArray(_ref, 3);\n\n var context = _ref2[0];\n var type = _ref2[1];\n var listener = _ref2[2];\n\n context.removeEventListener(type, listener);\n });\n this._listeners = [];\n }\n\n // This is primarily useful for programmatically simulating events on the\n // editor from the tests.\n }, {\n key: '_trigger',\n value: function _trigger(context, type, event) {\n (0, _mobiledocKitUtilsArrayUtils.forEach)((0, _mobiledocKitUtilsArrayUtils.filter)(this._listeners, function (_ref3) {\n var _ref32 = _slicedToArray(_ref3, 2);\n\n var _context = _ref32[0];\n var _type = _ref32[1];\n\n return _context === context && _type === type;\n }), function (_ref4) {\n var _ref42 = _slicedToArray(_ref4, 3);\n\n var context = _ref42[0];\n var type = _ref42[1];\n var listener = _ref42[2];\n\n listener.call(context, event);\n });\n }\n }, {\n key: 'destroy',\n value: function destroy() {\n this._textInputHandler.destroy();\n this._selectionManager.destroy();\n this._removeListeners();\n }\n }, {\n key: '_handleEvent',\n value: function _handleEvent(type, event) {\n var element = event.target;\n\n if (!this.isElementAddressable(element)) {\n // abort handling this event\n return true;\n }\n\n this[type](event);\n }\n }, {\n key: 'isElementAddressable',\n value: function isElementAddressable(element) {\n return this.editor.cursor.isAddressable(element);\n }\n }, {\n key: 'selectionDidChange',\n value: function selectionDidChange(selection /*, prevSelection */) {\n var shouldNotify = true;\n var anchorNode = selection.anchorNode;\n\n if (!this.isElementAddressable(anchorNode)) {\n if (!this.editor.range.isBlank) {\n // Selection changed from something addressable to something\n // not-addressable -- e.g., blur event, user clicked outside editor,\n // etc\n shouldNotify = true;\n } else {\n // selection changes wholly outside the editor should not trigger\n // change notifications\n shouldNotify = false;\n }\n }\n\n if (shouldNotify) {\n this.editor._readRangeFromDOM();\n }\n }\n }, {\n key: 'keypress',\n value: function keypress(event) {\n var editor = this.editor;\n var _textInputHandler = this._textInputHandler;\n\n if (!editor.hasCursor()) {\n return;\n }\n\n var key = _mobiledocKitUtilsKey['default'].fromEvent(event);\n if (!key.isPrintable()) {\n return;\n } else {\n event.preventDefault();\n }\n\n _textInputHandler.handle(key.toString());\n }\n }, {\n key: 'keydown',\n value: function keydown(event) {\n var editor = this.editor;\n\n if (!editor.hasCursor()) {\n return;\n }\n if (!editor.isEditable) {\n return;\n }\n\n var key = _mobiledocKitUtilsKey['default'].fromEvent(event);\n this._updateModifiersFromKey(key, { isDown: true });\n\n if (editor.handleKeyCommand(event)) {\n return;\n }\n\n if (editor.post.isBlank) {\n editor._insertEmptyMarkupSectionAtCursor();\n }\n\n var range = editor.range;\n\n switch (true) {\n // FIXME This should be restricted to only card/atom boundaries\n case key.isHorizontalArrowWithoutModifiersOtherThanShift():\n var newRange = undefined;\n if (key.isShift()) {\n newRange = range.extend(key.direction * 1);\n } else {\n newRange = range.move(key.direction);\n }\n\n editor.selectRange(newRange);\n event.preventDefault();\n break;\n case key.isDelete():\n var direction = key.direction;\n\n var unit = 'char';\n if (this.modifierKeys.alt && _mobiledocKitUtilsBrowser['default'].isMac()) {\n unit = 'word';\n } else if (this.modifierKeys.ctrl && _mobiledocKitUtilsBrowser['default'].isWin()) {\n unit = 'word';\n }\n editor.performDelete({ direction: direction, unit: unit });\n event.preventDefault();\n break;\n case key.isEnter():\n editor.handleNewline(event);\n break;\n case key.isTab():\n // Handle tab here because it does not fire a `keypress` event\n event.preventDefault();\n this._textInputHandler.handle(key.toString());\n break;\n }\n }\n }, {\n key: 'keyup',\n value: function keyup(event) {\n var editor = this.editor;\n\n if (!editor.hasCursor()) {\n return;\n }\n var key = _mobiledocKitUtilsKey['default'].fromEvent(event);\n this._updateModifiersFromKey(key, { isDown: false });\n }\n }, {\n key: 'cut',\n value: function cut(event) {\n event.preventDefault();\n\n this.copy(event);\n this.editor.performDelete();\n }\n }, {\n key: 'copy',\n value: function copy(event) {\n event.preventDefault();\n\n var editor = this.editor;\n var _editor = this.editor;\n var range = _editor.range;\n var post = _editor.post;\n\n post = post.trimTo(range);\n\n var data = {\n html: editor.serializePost(post, 'html'),\n text: editor.serializePost(post, 'text'),\n mobiledoc: editor.serializePost(post, 'mobiledoc')\n };\n\n (0, _mobiledocKitUtilsParseUtils.setClipboardData)(event, data, window);\n }\n }, {\n key: 'paste',\n value: function paste(event) {\n event.preventDefault();\n\n var editor = this.editor;\n\n var range = editor.range;\n\n if (!range.isCollapsed) {\n editor.performDelete();\n }\n\n if (editor.post.isBlank) {\n editor._insertEmptyMarkupSectionAtCursor();\n }\n\n var position = editor.range.head;\n var targetFormat = this.modifierKeys.shift ? 'text' : 'html';\n var pastedPost = (0, _mobiledocKitUtilsParseUtils.parsePostFromPaste)(event, editor, { targetFormat: targetFormat });\n\n editor.run(function (postEditor) {\n var nextPosition = postEditor.insertPost(position, pastedPost);\n postEditor.setRange(nextPosition);\n });\n }\n }, {\n key: 'drop',\n value: function drop(event) {\n event.preventDefault();\n\n var x = event.clientX;\n var y = event.clientY;\n var editor = this.editor;\n\n var position = editor.positionAtPoint(x, y);\n if (!position) {\n this.logger.log('Could not find drop position');\n return;\n }\n\n var post = (0, _mobiledocKitUtilsParseUtils.parsePostFromDrop)(event, editor, { logger: this.logger });\n if (!post) {\n this.logger.log('Could not determine post from drop event');\n return;\n }\n\n editor.run(function (postEditor) {\n var nextPosition = postEditor.insertPost(position, post);\n postEditor.setRange(nextPosition);\n });\n }\n }, {\n key: '_updateModifiersFromKey',\n value: function _updateModifiersFromKey(key, _ref5) {\n var isDown = _ref5.isDown;\n\n if (key.isShiftKey()) {\n this.modifierKeys.shift = isDown;\n } else if (key.isAltKey()) {\n this.modifierKeys.alt = isDown;\n } else if (key.isCtrlKey()) {\n this.modifierKeys.ctrl = isDown;\n }\n }\n }]);\n\n return EventManager;\n })();\n\n exports['default'] = EventManager;\n});","define('mobiledoc-kit/editor/key-commands', ['exports', 'mobiledoc-kit/utils/key', 'mobiledoc-kit/utils/array-utils', 'mobiledoc-kit/utils/assert', 'mobiledoc-kit/utils/browser', 'mobiledoc-kit/editor/ui'], function (exports, _mobiledocKitUtilsKey, _mobiledocKitUtilsArrayUtils, _mobiledocKitUtilsAssert, _mobiledocKitUtilsBrowser, _mobiledocKitEditorUi) {\n 'use strict';\n\n exports.buildKeyCommand = buildKeyCommand;\n exports.validateKeyCommand = validateKeyCommand;\n exports.findKeyCommands = findKeyCommands;\n\n function _toArray(arr) { return Array.isArray(arr) ? arr : Array.from(arr); }\n\n function selectAll(editor) {\n var post = editor.post;\n\n editor.selectRange(post.toRange());\n }\n\n function gotoStartOfLine(editor) {\n var range = editor.range;\n var section = range.tail.section;\n\n editor.run(function (postEditor) {\n postEditor.setRange(section.headPosition());\n });\n }\n\n function gotoEndOfLine(editor) {\n var range = editor.range;\n var section = range.tail.section;\n\n editor.run(function (postEditor) {\n postEditor.setRange(section.tailPosition());\n });\n }\n\n function deleteToEndOfSection(editor) {\n var range = editor.range;\n\n if (range.isCollapsed) {\n var _range = range;\n var head = _range.head;\n var section = _range.head.section;\n\n range = head.toRange(section.tailPosition());\n }\n editor.run(function (postEditor) {\n var nextPosition = postEditor.deleteRange(range);\n postEditor.setRange(nextPosition);\n });\n }\n\n var DEFAULT_KEY_COMMANDS = [{\n str: 'META+B',\n run: function run(editor) {\n editor.toggleMarkup('strong');\n }\n }, {\n str: 'CTRL+B',\n run: function run(editor) {\n editor.toggleMarkup('strong');\n }\n }, {\n str: 'META+I',\n run: function run(editor) {\n editor.toggleMarkup('em');\n }\n }, {\n str: 'CTRL+I',\n run: function run(editor) {\n editor.toggleMarkup('em');\n }\n }, {\n str: 'META+U',\n run: function run(editor) {\n editor.toggleMarkup('u');\n }\n }, {\n str: 'CTRL+U',\n run: function run(editor) {\n editor.toggleMarkup('u');\n }\n }, {\n str: 'CTRL+K',\n run: function run(editor) {\n if (_mobiledocKitUtilsBrowser['default'].isMac()) {\n return deleteToEndOfSection(editor);\n } else if (_mobiledocKitUtilsBrowser['default'].isWin()) {\n return (0, _mobiledocKitEditorUi.toggleLink)(editor);\n }\n }\n }, {\n str: 'CTRL+A',\n run: function run(editor) {\n if (_mobiledocKitUtilsBrowser['default'].isMac()) {\n gotoStartOfLine(editor);\n } else {\n selectAll(editor);\n }\n }\n }, {\n str: 'META+A',\n run: function run(editor) {\n if (_mobiledocKitUtilsBrowser['default'].isMac()) {\n selectAll(editor);\n }\n }\n }, {\n str: 'CTRL+E',\n run: function run(editor) {\n if (_mobiledocKitUtilsBrowser['default'].isMac()) {\n gotoEndOfLine(editor);\n }\n }\n }, {\n str: 'META+K',\n run: function run(editor) {\n return (0, _mobiledocKitEditorUi.toggleLink)(editor);\n }\n\n }, {\n str: 'META+Z',\n run: function run(editor) {\n editor.run(function (postEditor) {\n postEditor.undoLastChange();\n });\n }\n }, {\n str: 'META+SHIFT+Z',\n run: function run(editor) {\n editor.run(function (postEditor) {\n postEditor.redoLastChange();\n });\n }\n }, {\n str: 'CTRL+Z',\n run: function run(editor) {\n if (_mobiledocKitUtilsBrowser['default'].isMac()) {\n return false;\n }\n editor.run(function (postEditor) {\n return postEditor.undoLastChange();\n });\n }\n }, {\n str: 'CTRL+SHIFT+Z',\n run: function run(editor) {\n if (_mobiledocKitUtilsBrowser['default'].isMac()) {\n return false;\n }\n editor.run(function (postEditor) {\n return postEditor.redoLastChange();\n });\n }\n }];\n\n exports.DEFAULT_KEY_COMMANDS = DEFAULT_KEY_COMMANDS;\n function modifierNamesToMask(modiferNames) {\n var defaultVal = 0;\n return (0, _mobiledocKitUtilsArrayUtils.reduce)(modiferNames, function (sum, name) {\n var modifier = _mobiledocKitUtilsKey.MODIFIERS[name.toUpperCase()];\n (0, _mobiledocKitUtilsAssert['default'])('No modifier named \"' + name + '\" found', !!modifier);\n return sum + modifier;\n }, defaultVal);\n }\n\n function characterToCode(character) {\n var upperCharacter = character.toUpperCase();\n var special = _mobiledocKitUtilsKey.SPECIAL_KEYS[upperCharacter];\n if (special) {\n return special;\n } else {\n (0, _mobiledocKitUtilsAssert['default'])('Only 1 character can be used in a key command str (got \"' + character + '\")', character.length === 1);\n return upperCharacter.charCodeAt(0);\n }\n }\n\n function buildKeyCommand(keyCommand) {\n var str = keyCommand.str;\n\n if (!str) {\n return keyCommand;\n }\n (0, _mobiledocKitUtilsAssert['default'])('[deprecation] Key commands no longer use the `modifier` property', !keyCommand.modifier);\n\n var _str$split$reverse = str.split('+').reverse();\n\n var _str$split$reverse2 = _toArray(_str$split$reverse);\n\n var character = _str$split$reverse2[0];\n\n var modifierNames = _str$split$reverse2.slice(1);\n\n keyCommand.modifierMask = modifierNamesToMask(modifierNames);\n keyCommand.code = characterToCode(character);\n\n return keyCommand;\n }\n\n function validateKeyCommand(keyCommand) {\n return !!keyCommand.code && !!keyCommand.run;\n }\n\n function findKeyCommands(keyCommands, keyEvent) {\n var key = _mobiledocKitUtilsKey['default'].fromEvent(keyEvent);\n\n return (0, _mobiledocKitUtilsArrayUtils.filter)(keyCommands, function (_ref) {\n var modifierMask = _ref.modifierMask;\n var code = _ref.code;\n\n return key.keyCode === code && key.modifierMask === modifierMask;\n });\n }\n});","define('mobiledoc-kit/editor/mutation-handler', ['exports', 'mobiledoc-kit/utils/set', 'mobiledoc-kit/utils/array-utils', 'mobiledoc-kit/utils/assert', 'mobiledoc-kit/utils/dom-utils'], function (exports, _mobiledocKitUtilsSet, _mobiledocKitUtilsArrayUtils, _mobiledocKitUtilsAssert, _mobiledocKitUtilsDomUtils) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n var MUTATION = {\n NODES_CHANGED: 'childList',\n CHARACTER_DATA: 'characterData'\n };\n\n var MutationHandler = (function () {\n function MutationHandler(editor) {\n var _this = this;\n\n _classCallCheck(this, MutationHandler);\n\n this.editor = editor;\n this.logger = editor.loggerFor('mutation-handler');\n this.renderTree = null;\n this._isObserving = false;\n\n this._observer = new MutationObserver(function (mutations) {\n _this._handleMutations(mutations);\n });\n }\n\n _createClass(MutationHandler, [{\n key: 'init',\n value: function init() {\n this.startObserving();\n }\n }, {\n key: 'destroy',\n value: function destroy() {\n this.stopObserving();\n this._observer = null;\n }\n }, {\n key: 'suspendObservation',\n value: function suspendObservation(callback) {\n this.stopObserving();\n callback();\n this.startObserving();\n }\n }, {\n key: 'stopObserving',\n value: function stopObserving() {\n if (this._isObserving) {\n this._isObserving = false;\n this._observer.disconnect();\n }\n }\n }, {\n key: 'startObserving',\n value: function startObserving() {\n if (!this._isObserving) {\n var editor = this.editor;\n\n (0, _mobiledocKitUtilsAssert['default'])('Cannot observe un-rendered editor', editor.hasRendered);\n\n this._isObserving = true;\n this.renderTree = editor._renderTree;\n\n this._observer.observe(editor.element, {\n characterData: true,\n childList: true,\n subtree: true\n });\n }\n }\n }, {\n key: 'reparsePost',\n value: function reparsePost() {\n this.editor._reparsePost();\n }\n }, {\n key: 'reparseSections',\n value: function reparseSections(sections) {\n this.editor._reparseSections(sections);\n }\n\n /**\n * for each mutation:\n * * find the target nodes:\n * * if nodes changed, target nodes are:\n * * added nodes\n * * the target from which removed nodes were removed\n * * if character data changed\n * * target node is the mutation event's target (text node)\n * * filter out nodes that are no longer attached (parentNode is null)\n * * for each remaining node:\n * * find its section, add to sections-to-reparse\n * * if no section, reparse all (and break)\n */\n }, {\n key: '_handleMutations',\n value: function _handleMutations(mutations) {\n var reparsePost = false;\n var sections = new _mobiledocKitUtilsSet['default']();\n\n for (var i = 0; i < mutations.length; i++) {\n if (reparsePost) {\n break;\n }\n\n var nodes = this._findTargetNodes(mutations[i]);\n\n for (var j = 0; j < nodes.length; j++) {\n var node = nodes[j];\n var renderNode = this._findRenderNodeFromNode(node);\n if (renderNode) {\n if (renderNode.reparsesMutationOfChildNode(node)) {\n var section = this._findSectionFromRenderNode(renderNode);\n if (section) {\n sections.add(section);\n } else {\n reparsePost = true;\n }\n }\n } else {\n reparsePost = true;\n break;\n }\n }\n }\n\n if (reparsePost) {\n this.logger.log('reparsePost (' + mutations.length + ' mutations)');\n this.reparsePost();\n } else if (sections.length) {\n this.logger.log('reparse ' + sections.length + ' sections (' + mutations.length + ' mutations)');\n this.reparseSections(sections.toArray());\n }\n }\n }, {\n key: '_findTargetNodes',\n value: function _findTargetNodes(mutation) {\n var nodes = [];\n\n switch (mutation.type) {\n case MUTATION.CHARACTER_DATA:\n nodes.push(mutation.target);\n break;\n case MUTATION.NODES_CHANGED:\n (0, _mobiledocKitUtilsArrayUtils.forEach)(mutation.addedNodes, function (n) {\n return nodes.push(n);\n });\n if (mutation.removedNodes.length) {\n nodes.push(mutation.target);\n }\n break;\n }\n\n var element = this.editor.element;\n var attachedNodes = (0, _mobiledocKitUtilsArrayUtils.filter)(nodes, function (node) {\n return (0, _mobiledocKitUtilsDomUtils.containsNode)(element, node);\n });\n return attachedNodes;\n }\n }, {\n key: '_findSectionRenderNodeFromNode',\n value: function _findSectionRenderNodeFromNode(node) {\n return this.renderTree.findRenderNodeFromElement(node, function (rn) {\n return rn.postNode.isSection;\n });\n }\n }, {\n key: '_findRenderNodeFromNode',\n value: function _findRenderNodeFromNode(node) {\n return this.renderTree.findRenderNodeFromElement(node);\n }\n }, {\n key: '_findSectionFromRenderNode',\n value: function _findSectionFromRenderNode(renderNode) {\n var sectionRenderNode = this._findSectionRenderNodeFromNode(renderNode.element);\n return sectionRenderNode && sectionRenderNode.postNode;\n }\n }]);\n\n return MutationHandler;\n })();\n\n exports['default'] = MutationHandler;\n});","define('mobiledoc-kit/editor/post', ['exports', 'mobiledoc-kit/utils/cursor/position', 'mobiledoc-kit/utils/cursor/range', 'mobiledoc-kit/utils/array-utils', 'mobiledoc-kit/utils/key', 'mobiledoc-kit/models/lifecycle-callbacks', 'mobiledoc-kit/utils/assert', 'mobiledoc-kit/utils/dom-utils', 'mobiledoc-kit/editor/post/post-inserter', 'mobiledoc-kit/utils/deprecate', 'mobiledoc-kit/utils/to-range'], function (exports, _mobiledocKitUtilsCursorPosition, _mobiledocKitUtilsCursorRange, _mobiledocKitUtilsArrayUtils, _mobiledocKitUtilsKey, _mobiledocKitModelsLifecycleCallbacks, _mobiledocKitUtilsAssert, _mobiledocKitUtilsDomUtils, _mobiledocKitEditorPostPostInserter, _mobiledocKitUtilsDeprecate, _mobiledocKitUtilsToRange) {\n 'use strict';\n\n var _slicedToArray = (function () { function sliceIterator(arr, i) { var _arr = []; var _n = true; var _d = false; var _e = undefined; try { for (var _i = arr[Symbol.iterator](), _s; !(_n = (_s = _i.next()).done); _n = true) { _arr.push(_s.value); if (i && _arr.length === i) break; } } catch (err) { _d = true; _e = err; } finally { try { if (!_n && _i['return']) _i['return'](); } finally { if (_d) throw _e; } } return _arr; } return function (arr, i) { if (Array.isArray(arr)) { return arr; } else if (Symbol.iterator in Object(arr)) { return sliceIterator(arr, i); } else { throw new TypeError('Invalid attempt to destructure non-iterable instance'); } }; })();\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n var FORWARD = _mobiledocKitUtilsKey.DIRECTION.FORWARD;\n var BACKWARD = _mobiledocKitUtilsKey.DIRECTION.BACKWARD;\n\n function isListSectionTagName(tagName) {\n return tagName === 'ul' || tagName === 'ol';\n }\n\n var CALLBACK_QUEUES = {\n BEFORE_COMPLETE: 'beforeComplete',\n COMPLETE: 'complete',\n AFTER_COMPLETE: 'afterComplete'\n };\n\n // There are only two events that we're concerned about for Undo, that is inserting text and deleting content.\n // These are the only two states that go on a \"run\" and create a combined undo, everything else has it's own\n // deadicated undo.\n var EDIT_ACTIONS = {\n INSERT_TEXT: 1,\n DELETE: 2\n };\n\n /**\n * The PostEditor is used to modify a post. It should not be instantiated directly.\n * Instead, a new instance of a PostEditor is created by the editor and passed\n * as the argument to the callback in {@link Editor#run}.\n *\n * Usage:\n * ```\n * editor.run((postEditor) => {\n * // postEditor is an instance of PostEditor that can operate on the\n * // editor's post\n * });\n * ```\n */\n\n var PostEditor = (function () {\n /**\n * @private\n */\n\n function PostEditor(editor) {\n var _this = this;\n\n _classCallCheck(this, PostEditor);\n\n this.editor = editor;\n this.builder = this.editor.builder;\n this._callbacks = new _mobiledocKitModelsLifecycleCallbacks['default']((0, _mobiledocKitUtilsArrayUtils.values)(CALLBACK_QUEUES));\n\n this._didComplete = false;\n this.editActionTaken = null;\n\n this._renderRange = function () {\n return _this.editor.selectRange(_this._range);\n };\n this._postDidChange = function () {\n return _this.editor._postDidChange();\n };\n this._rerender = function () {\n return _this.editor.rerender();\n };\n }\n\n _createClass(PostEditor, [{\n key: 'addCallback',\n value: function addCallback() {\n var _callbacks;\n\n (_callbacks = this._callbacks).addCallback.apply(_callbacks, arguments);\n }\n }, {\n key: 'addCallbackOnce',\n value: function addCallbackOnce() {\n var _callbacks2;\n\n (_callbacks2 = this._callbacks).addCallbackOnce.apply(_callbacks2, arguments);\n }\n }, {\n key: 'runCallbacks',\n value: function runCallbacks() {\n var _callbacks3;\n\n (_callbacks3 = this._callbacks).runCallbacks.apply(_callbacks3, arguments);\n }\n }, {\n key: 'begin',\n value: function begin() {\n // cache the editor's range\n this._range = this.editor.range;\n }\n\n /**\n * Schedules to select the given range on the editor after the postEditor\n * has completed its work. This also updates the postEditor's active range\n * (so that multiple calls to range-changing methods on the postEditor will\n * update the correct range).\n *\n * Usage:\n * let range = editor.range;\n * editor.run(postEditor => {\n * let nextPosition = postEditor.deleteRange(range);\n *\n * // Will position the editor's cursor at `nextPosition` after\n * // the postEditor finishes work and the editor rerenders.\n * postEditor.setRange(nextPosition);\n * });\n * @param {Range|Position} range\n * @public\n */\n }, {\n key: 'setRange',\n value: function setRange(range) {\n range = (0, _mobiledocKitUtilsToRange['default'])(range);\n\n // TODO validate that the range is valid\n // (does not contain marked-for-removal head or tail sections?)\n this._range = range;\n this.scheduleAfterRender(this._renderRange, true);\n }\n\n /**\n * Delete a range from the post\n *\n * Usage:\n * ```\n * let { range } = editor;\n * editor.run((postEditor) => {\n * let nextPosition = postEditor.deleteRange(range);\n * postEditor.setRange(nextPosition);\n * });\n * ```\n * @param {Range} range Cursor Range object with head and tail Positions\n * @return {Position} The position where the cursor would go after deletion\n * @public\n */\n }, {\n key: 'deleteRange',\n value: function deleteRange(range) {\n (0, _mobiledocKitUtilsAssert['default'])(\"Must pass MobiledocKit Range to `deleteRange`\", range instanceof _mobiledocKitUtilsCursorRange['default']);\n\n this.editActionTaken = EDIT_ACTIONS.DELETE;\n\n var head = range.head;\n var headSection = range.head.section;\n var tail = range.tail;\n var tailSection = range.tail.section;\n var post = this.editor.post;\n\n if (headSection === tailSection) {\n return this.cutSection(headSection, head, tail);\n }\n\n var nextSection = headSection.nextLeafSection();\n\n var nextPos = this.cutSection(headSection, head, headSection.tailPosition());\n // cutSection can replace the section, so re-read headSection here\n headSection = nextPos.section;\n\n // Remove sections in the middle of the range\n while (nextSection !== tailSection) {\n var tmp = nextSection;\n nextSection = nextSection.nextLeafSection();\n this.removeSection(tmp);\n }\n\n var tailPos = this.cutSection(tailSection, tailSection.headPosition(), tail);\n // cutSection can replace the section, so re-read tailSection here\n tailSection = tailPos.section;\n\n if (tailSection.isBlank) {\n this.removeSection(tailSection);\n } else {\n // If head and tail sections are markerable, join them\n // Note: They may not be the same section type. E.g. this may join\n // a tail section that was a list item onto a markup section, or vice versa.\n // (This is the desired behavior.)\n if (headSection.isMarkerable && tailSection.isMarkerable) {\n headSection.join(tailSection);\n this._markDirty(headSection);\n this.removeSection(tailSection);\n } else if (headSection.isBlank) {\n this.removeSection(headSection);\n nextPos = tailPos;\n }\n }\n\n if (post.isBlank) {\n post.sections.append(this.builder.createMarkupSection('p'));\n nextPos = post.headPosition();\n }\n\n return nextPos;\n }\n\n /**\n * Note: This method may replace `section` with a different section.\n *\n * \"Cut\" out the part of the section inside `headOffset` and `tailOffset`.\n * If section is markerable this splits markers that straddle the head or tail (if necessary),\n * and removes markers that are wholly inside the offsets.\n * If section is a card, this may replace it with a blank markup section if the\n * positions contain the entire card.\n *\n * @param {Section} section\n * @param {Position} head\n * @param {Position} tail\n * @return {Position}\n * @private\n */\n }, {\n key: 'cutSection',\n value: function cutSection(section, head, tail) {\n var _this2 = this;\n\n (0, _mobiledocKitUtilsAssert['default'])('Must pass head position and tail position to `cutSection`', head instanceof _mobiledocKitUtilsCursorPosition['default'] && tail instanceof _mobiledocKitUtilsCursorPosition['default']);\n (0, _mobiledocKitUtilsAssert['default'])('Must pass positions within same section to `cutSection`', head.section === tail.section);\n\n if (section.isBlank || head.isEqual(tail)) {\n return head;\n }\n if (section.isCardSection) {\n if (head.isHead() && tail.isTail()) {\n var newSection = this.builder.createMarkupSection();\n this.replaceSection(section, newSection);\n return newSection.headPosition();\n } else {\n return tail;\n }\n }\n\n var range = head.toRange(tail);\n this.splitMarkers(range).forEach(function (m) {\n return _this2.removeMarker(m);\n });\n\n return head;\n }\n }, {\n key: '_coalesceMarkers',\n value: function _coalesceMarkers(section) {\n if (section.isMarkerable) {\n this._removeBlankMarkers(section);\n this._joinSimilarMarkers(section);\n }\n }\n }, {\n key: '_removeBlankMarkers',\n value: function _removeBlankMarkers(section) {\n var _this3 = this;\n\n (0, _mobiledocKitUtilsArrayUtils.forEach)((0, _mobiledocKitUtilsArrayUtils.filter)(section.markers, function (m) {\n return m.isBlank;\n }), function (m) {\n return _this3.removeMarker(m);\n });\n }\n\n // joins markers that have identical markups\n }, {\n key: '_joinSimilarMarkers',\n value: function _joinSimilarMarkers(section) {\n var marker = section.markers.head;\n var nextMarker = undefined;\n while (marker && marker.next) {\n nextMarker = marker.next;\n\n if (marker.canJoin(nextMarker)) {\n nextMarker.value = marker.value + nextMarker.value;\n this._markDirty(nextMarker);\n this.removeMarker(marker);\n }\n\n marker = nextMarker;\n }\n }\n }, {\n key: 'removeMarker',\n value: function removeMarker(marker) {\n this._scheduleForRemoval(marker);\n if (marker.section) {\n this._markDirty(marker.section);\n marker.section.markers.remove(marker);\n }\n }\n }, {\n key: '_scheduleForRemoval',\n value: function _scheduleForRemoval(postNode) {\n var _this4 = this;\n\n if (postNode.renderNode) {\n postNode.renderNode.scheduleForRemoval();\n\n this.scheduleRerender();\n this.scheduleDidUpdate();\n }\n var removedAdjacentToList = postNode.prev && postNode.prev.isListSection || postNode.next && postNode.next.isListSection;\n if (removedAdjacentToList) {\n this.addCallback(CALLBACK_QUEUES.BEFORE_COMPLETE, function () {\n return _this4._joinContiguousListSections();\n });\n }\n }\n }, {\n key: '_joinContiguousListSections',\n value: function _joinContiguousListSections() {\n var _this5 = this;\n\n var post = this.editor.post;\n\n var range = this._range;\n var prev = undefined;\n var groups = [];\n var currentGroup = undefined;\n\n // FIXME do we need to force a re-render of the range if changed sections\n // are contained within the range?\n var updatedHead = null;\n (0, _mobiledocKitUtilsArrayUtils.forEach)(post.sections, function (section) {\n if (prev && prev.isListSection && section.isListSection && prev.tagName === section.tagName) {\n\n currentGroup = currentGroup || [prev];\n currentGroup.push(section);\n } else {\n if (currentGroup) {\n groups.push(currentGroup);\n }\n currentGroup = null;\n }\n prev = section;\n });\n\n if (currentGroup) {\n groups.push(currentGroup);\n }\n\n (0, _mobiledocKitUtilsArrayUtils.forEach)(groups, function (group) {\n var list = group[0];\n (0, _mobiledocKitUtilsArrayUtils.forEach)(group, function (listSection) {\n if (listSection === list) {\n return;\n }\n\n var currentHead = range.head;\n var prevPosition = undefined;\n\n // FIXME is there a currentHead if there is no range?\n // is the current head a list item in the section\n if (!range.isBlank && currentHead.section.isListItem && currentHead.section.parent === listSection) {\n prevPosition = list.tailPosition();\n }\n _this5._joinListSections(list, listSection);\n if (prevPosition) {\n updatedHead = prevPosition.move(FORWARD);\n }\n });\n });\n\n if (updatedHead) {\n this.setRange(updatedHead);\n }\n }\n }, {\n key: '_joinListSections',\n value: function _joinListSections(baseList, nextList) {\n baseList.join(nextList);\n this._markDirty(baseList);\n this.removeSection(nextList);\n }\n }, {\n key: '_markDirty',\n value: function _markDirty(postNode) {\n var _this6 = this;\n\n if (postNode.renderNode) {\n postNode.renderNode.markDirty();\n\n this.scheduleRerender();\n this.scheduleDidUpdate();\n }\n if (postNode.section) {\n this._markDirty(postNode.section);\n }\n if (postNode.isMarkerable) {\n this.addCallback(CALLBACK_QUEUES.BEFORE_COMPLETE, function () {\n return _this6._coalesceMarkers(postNode);\n });\n }\n }\n\n /**\n * @param {Position} position object with {section, offset} the marker and offset to delete from\n * @param {Number} direction The direction to delete in (default is BACKWARD)\n * @return {Position} for positioning the cursor\n * @public\n * @deprecated after v0.10.3\n */\n }, {\n key: 'deleteFrom',\n value: function deleteFrom(position) {\n var direction = arguments.length <= 1 || arguments[1] === undefined ? _mobiledocKitUtilsKey.DIRECTION.BACKWARD : arguments[1];\n\n (0, _mobiledocKitUtilsDeprecate['default'])(\"`postEditor#deleteFrom is deprecated. Use `deleteAtPosition(position, direction=BACKWARD, {unit}={unit: 'char'})` instead\");\n return this.deleteAtPosition(position, direction, { unit: 'char' });\n }\n\n /**\n * Delete 1 `unit` (can be 'char' or 'word') in the given `direction` at the given\n * `position`. In almost all cases this will be equivalent to deleting the range formed\n * by expanding the position 1 unit in the given direction. The exception is when deleting\n * backward from the beginning of a list item, which reverts the list item into a markup section\n * instead of joining it with its previous list item (if any).\n *\n * Usage:\n *\n * let position = section.tailPosition();\n * // Section has text of \"Howdy!\"\n * editor.run((postEditor) => {\n * postEditor.deleteAtPosition(position);\n * });\n * // section has text of \"Howdy\"\n *\n * @param {Position} position The position to delete at\n * @param {Direction} [direction=DIRECTION.BACKWARD] direction The direction to delete in\n * @param {Object} [options]\n * @param {String} [options.unit=\"char\"] The unit of deletion (\"word\" or \"char\")\n * @return {Position}\n */\n }, {\n key: 'deleteAtPosition',\n value: function deleteAtPosition(position) {\n var direction = arguments.length <= 1 || arguments[1] === undefined ? _mobiledocKitUtilsKey.DIRECTION.BACKWARD : arguments[1];\n\n var _ref = arguments.length <= 2 || arguments[2] === undefined ? { unit: 'char' } : arguments[2];\n\n var unit = _ref.unit;\n\n if (direction === _mobiledocKitUtilsKey.DIRECTION.BACKWARD) {\n return this._deleteAtPositionBackward(position, unit);\n } else {\n return this._deleteAtPositionForward(position, unit);\n }\n }\n }, {\n key: '_deleteAtPositionBackward',\n value: function _deleteAtPositionBackward(position, unit) {\n if (position.isHead() && position.section.isListItem) {\n this.toggleSection('p', position);\n return this._range.head;\n } else {\n var prevPosition = unit === 'word' ? position.moveWord(BACKWARD) : position.move(BACKWARD);\n var range = prevPosition.toRange(position);\n return this.deleteRange(range);\n }\n }\n }, {\n key: '_deleteAtPositionForward',\n value: function _deleteAtPositionForward(position, unit) {\n var nextPosition = unit === 'word' ? position.moveWord(FORWARD) : position.move(FORWARD);\n var range = position.toRange(nextPosition);\n return this.deleteRange(range);\n }\n\n /**\n * Split markers at two positions, once at the head, and if necessary once\n * at the tail.\n *\n * Usage:\n * ```\n * let range = editor.range;\n * editor.run((postEditor) => {\n * postEditor.splitMarkers(range);\n * });\n * ```\n * The return value will be marker object completely inside the offsets\n * provided. Markers outside of the split may also have been modified.\n *\n * @param {Range} markerRange\n * @return {Array} of markers that are inside the split\n * @private\n */\n }, {\n key: 'splitMarkers',\n value: function splitMarkers(range) {\n var post = this.editor.post;\n var head = range.head;\n var tail = range.tail;\n\n this.splitSectionMarkerAtOffset(head.section, head.offset);\n this.splitSectionMarkerAtOffset(tail.section, tail.offset);\n\n return post.markersContainedByRange(range);\n }\n }, {\n key: 'splitSectionMarkerAtOffset',\n value: function splitSectionMarkerAtOffset(section, offset) {\n var _this7 = this;\n\n var edit = section.splitMarkerAtOffset(offset);\n edit.removed.forEach(function (m) {\n return _this7.removeMarker(m);\n });\n }\n\n /**\n * Split the section at the position.\n *\n * Usage:\n * ```\n * let position = editor.cursor.offsets.head;\n * editor.run((postEditor) => {\n * postEditor.splitSection(position);\n * });\n * // Will result in the creation of two new sections\n * // replacing the old one at the cursor position\n * ```\n * The return value will be the two new sections. One or both of these\n * sections can be blank (contain only a blank marker), for example if the\n * headMarkerOffset is 0.\n *\n * @param {Position} position\n * @return {Array} new sections, one for the first half and one for the second (either one can be null)\n * @public\n */\n }, {\n key: 'splitSection',\n value: function splitSection(position) {\n var _this8 = this;\n\n var section = position.section;\n\n if (section.isCardSection) {\n return this._splitCardSection(section, position);\n } else if (section.isListItem) {\n var isLastAndBlank = section.isBlank && !section.next;\n if (isLastAndBlank) {\n // if is last, replace the item with a blank markup section\n var _parent = section.parent;\n var collection = this.editor.post.sections;\n var blank = this.builder.createMarkupSection();\n this.removeSection(section);\n this.insertSectionBefore(collection, blank, _parent.next);\n\n return [null, blank];\n } else {\n var _splitListItem2 = this._splitListItem(section, position);\n\n var _splitListItem22 = _slicedToArray(_splitListItem2, 2);\n\n var pre = _splitListItem22[0];\n var post = _splitListItem22[1];\n\n return [pre, post];\n }\n } else {\n var splitSections = section.splitAtPosition(position);\n splitSections.forEach(function (s) {\n return _this8._coalesceMarkers(s);\n });\n this._replaceSection(section, splitSections);\n\n return splitSections;\n }\n }\n\n /**\n * @param {Section} cardSection\n * @param {Position} position to split at\n * @return {Section[]} 2-item array of pre and post-split sections\n * @private\n */\n }, {\n key: '_splitCardSection',\n value: function _splitCardSection(cardSection, position) {\n var offset = position.offset;\n\n (0, _mobiledocKitUtilsAssert['default'])('Cards section must be split at offset 0 or 1', offset === 0 || offset === 1);\n\n var newSection = this.builder.createMarkupSection();\n var nextSection = undefined;\n var surroundingSections = undefined;\n\n if (offset === 0) {\n nextSection = cardSection;\n surroundingSections = [newSection, cardSection];\n } else {\n nextSection = cardSection.next;\n surroundingSections = [cardSection, newSection];\n }\n\n var collection = this.editor.post.sections;\n this.insertSectionBefore(collection, newSection, nextSection);\n\n return surroundingSections;\n }\n\n /**\n * @param {Section} section\n * @param {Section} newSection\n * @return null\n * @public\n */\n }, {\n key: 'replaceSection',\n value: function replaceSection(section, newSection) {\n if (!section) {\n // FIXME should a falsy section be a valid argument?\n this.insertSectionBefore(this.editor.post.sections, newSection, null);\n } else {\n this._replaceSection(section, [newSection]);\n }\n }\n }, {\n key: 'moveSectionBefore',\n value: function moveSectionBefore(collection, renderedSection, beforeSection) {\n var newSection = renderedSection.clone();\n this.removeSection(renderedSection);\n this.insertSectionBefore(collection, newSection, beforeSection);\n return newSection;\n }\n\n /**\n * @param {Section} section A section that is already in DOM\n * @public\n */\n }, {\n key: 'moveSectionUp',\n value: function moveSectionUp(renderedSection) {\n var isFirst = !renderedSection.prev;\n if (isFirst) {\n return renderedSection;\n }\n\n var collection = renderedSection.parent.sections;\n var beforeSection = renderedSection.prev;\n return this.moveSectionBefore(collection, renderedSection, beforeSection);\n }\n\n /**\n * @param {Section} section A section that is already in DOM\n * @public\n */\n }, {\n key: 'moveSectionDown',\n value: function moveSectionDown(renderedSection) {\n var isLast = !renderedSection.next;\n if (isLast) {\n return renderedSection;\n }\n\n var beforeSection = renderedSection.next.next;\n var collection = renderedSection.parent.sections;\n return this.moveSectionBefore(collection, renderedSection, beforeSection);\n }\n\n /**\n * Insert an array of markers at the given position. If the position is in\n * a non-markerable section (like a card section), this method throws an error.\n *\n * @param {Position} position\n * @param {Marker[]} markers\n * @return {Position} The position that represents the end of the inserted markers.\n * @public\n */\n }, {\n key: 'insertMarkers',\n value: function insertMarkers(position, markers) {\n var _this9 = this;\n\n var section = position.section;\n var offset = position.offset;\n\n (0, _mobiledocKitUtilsAssert['default'])('Cannot insert markers at non-markerable position', section.isMarkerable);\n\n this.editActionTaken = EDIT_ACTIONS.INSERT_TEXT;\n\n var edit = section.splitMarkerAtOffset(offset);\n edit.removed.forEach(function (marker) {\n return _this9._scheduleForRemoval(marker);\n });\n\n var prevMarker = section.markerBeforeOffset(offset);\n markers.forEach(function (marker) {\n section.markers.insertAfter(marker, prevMarker);\n offset += marker.length;\n prevMarker = marker;\n });\n\n this._coalesceMarkers(section);\n this._markDirty(section);\n\n var nextPosition = section.toPosition(offset);\n this.setRange(nextPosition);\n return nextPosition;\n }\n\n /**\n * Inserts text with the given markups, ignoring the existing markups at\n * the position, if any.\n *\n * @param {Position} position\n * @param {String} text\n * @param {Markup[]} markups\n * @return {Position} position at the end of the inserted text\n */\n }, {\n key: 'insertTextWithMarkup',\n value: function insertTextWithMarkup(position, text) {\n var markups = arguments.length <= 2 || arguments[2] === undefined ? [] : arguments[2];\n var section = position.section;\n\n if (!section.isMarkerable) {\n return;\n }\n var marker = this.builder.createMarker(text, markups);\n return this.insertMarkers(position, [marker]);\n }\n\n /**\n * Insert the text at the given position\n * Inherits the markups already at that position, if any.\n *\n * @param {Position} position\n * @param {String} text\n * @return {Position} position at the end of the inserted text.\n */\n }, {\n key: 'insertText',\n value: function insertText(position, text) {\n var section = position.section;\n\n if (!section.isMarkerable) {\n return;\n }\n var markups = position.marker && position.marker.markups;\n markups = markups || [];\n return this.insertTextWithMarkup(position, text, markups);\n }\n }, {\n key: '_replaceSection',\n value: function _replaceSection(section, newSections) {\n var _this10 = this;\n\n var nextSection = section.next;\n var collection = section.parent.sections;\n\n var nextNewSection = newSections[0];\n if (nextNewSection.isMarkupSection && section.isListItem) {\n // put the new section after the ListSection (section.parent)\n // instead of after the ListItem\n collection = section.parent.parent.sections;\n nextSection = section.parent.next;\n }\n\n newSections.forEach(function (s) {\n return _this10.insertSectionBefore(collection, s, nextSection);\n });\n this.removeSection(section);\n }\n\n /**\n * Given a markerRange (for example `editor.range`) mark all markers\n * inside it as a given markup. The markup must be provided as a post\n * abstract node.\n *\n * Usage:\n *\n * let range = editor.range;\n * let strongMarkup = editor.builder.createMarkup('strong');\n * editor.run((postEditor) => {\n * postEditor.addMarkupToRange(range, strongMarkup);\n * });\n * // Will result some markers possibly being split, and the markup\n * // being applied to all markers between the split.\n *\n * @param {Range} range\n * @param {Markup} markup A markup post abstract node\n * @public\n */\n }, {\n key: 'addMarkupToRange',\n value: function addMarkupToRange(range, markup) {\n var _this11 = this;\n\n if (range.isCollapsed) {\n return;\n }\n\n var markers = this.splitMarkers(range);\n if (markers.length) {\n (function () {\n // We insert the new markup at a consistent index across the range.\n // If we just push on the end of the list, it can end up in different positions\n // of the markup stack. This results in unnecessary closing and re-opening of\n // the markup each time it changes position.\n // If we just push it at the beginning of the list, this causes unnecessary closing\n // and re-opening of surrounding tags.\n // So, we look for any tags open across the whole range, and push into the stack\n // at the end of those.\n // Prompted by https://github.com/bustle/mobiledoc-kit/issues/360\n\n var markupsOpenAcrossRange = (0, _mobiledocKitUtilsArrayUtils.reduce)(markers, function (soFar, marker) {\n return (0, _mobiledocKitUtilsArrayUtils.commonItems)(soFar, marker.markups);\n }, markers[0].markups);\n var indexToInsert = markupsOpenAcrossRange.length;\n\n markers.forEach(function (marker) {\n marker.addMarkupAtIndex(markup, indexToInsert);\n _this11._markDirty(marker);\n });\n })();\n }\n }\n\n /**\n * Given a markerRange (for example `editor.range`) remove the given\n * markup from all contained markers.\n *\n * Usage:\n * ```\n * let { range } = editor;\n * let markup = markerRange.headMarker.markups[0];\n * editor.run(postEditor => {\n * postEditor.removeMarkupFromRange(range, markup);\n * });\n * // Will result in some markers possibly being split, and the markup\n * // being removed from all markers between the split.\n * ```\n * @param {Range} range Object with offsets\n * @param {Markup|Function} markupOrCallback A markup post abstract node or\n * a function that returns true when passed a markup that should be removed\n * @private\n */\n }, {\n key: 'removeMarkupFromRange',\n value: function removeMarkupFromRange(range, markupOrMarkupCallback) {\n var _this12 = this;\n\n if (range.isCollapsed) {\n return;\n }\n\n this.splitMarkers(range).forEach(function (marker) {\n marker.removeMarkup(markupOrMarkupCallback);\n _this12._markDirty(marker);\n });\n }\n\n /**\n * Toggle the given markup in the given range (or at the position given). If the range/position\n * has the markup, the markup will be removed. If nothing in the range/position\n * has the markup, the markup will be added to everything in the range/position.\n *\n * Usage:\n * ```\n * // Remove any 'strong' markup if it exists in the selection, otherwise\n * // make it all 'strong'\n * editor.run(postEditor => postEditor.toggleMarkup('strong'));\n *\n * // add/remove a link to 'bustle.com' to the selection\n * editor.run(postEditor => {\n * const linkMarkup = postEditor.builder.createMarkup('a', {href: 'http://bustle.com'});\n * postEditor.toggleMarkup(linkMarkup);\n * });\n * ```\n * @param {Markup|String} markupOrString Either a markup object created using\n * the builder (useful when adding a markup with attributes, like an 'a' markup),\n * or, if a string, the tag name of the markup (e.g. 'strong', 'em') to toggle.\n * @param {Range|Position} range in which to toggle. Defaults to current editor range.\n * @public\n */\n }, {\n key: 'toggleMarkup',\n value: function toggleMarkup(markupOrMarkupString) {\n var range = arguments.length <= 1 || arguments[1] === undefined ? this._range : arguments[1];\n\n range = (0, _mobiledocKitUtilsToRange['default'])(range);\n var markup = typeof markupOrMarkupString === 'string' ? this.builder.createMarkup(markupOrMarkupString) : markupOrMarkupString;\n\n var hasMarkup = this.editor.detectMarkupInRange(range, markup.tagName);\n // FIXME: This implies only a single markup in a range. This may not be\n // true for links (which are not the same object instance like multiple\n // strong tags would be).\n if (hasMarkup) {\n this.removeMarkupFromRange(range, hasMarkup);\n } else {\n this.addMarkupToRange(range, markup);\n }\n\n this.setRange(range);\n }\n\n /**\n * Toggles the tagName of the active section or sections in the given range/position.\n * If every section has the tag name, they will all be reset to default sections.\n * Otherwise, every section will be changed to the requested type\n *\n * @param {String} sectionTagName A valid markup section or\n * list section tag name (e.g. 'blockquote', 'h2', 'ul')\n * @param {Range|Position} range The range over which to toggle.\n * Defaults to the current editor range.\n * @public\n */\n }, {\n key: 'toggleSection',\n value: function toggleSection(sectionTagName) {\n var _this13 = this;\n\n var range = arguments.length <= 1 || arguments[1] === undefined ? this._range : arguments[1];\n\n range = (0, _mobiledocKitUtilsToRange['default'])(range);\n\n sectionTagName = (0, _mobiledocKitUtilsDomUtils.normalizeTagName)(sectionTagName);\n var post = this.editor.post;\n\n var nextRange = range;\n\n var everySectionHasTagName = true;\n post.walkMarkerableSections(range, function (section) {\n if (!_this13._isSameSectionType(section, sectionTagName)) {\n everySectionHasTagName = false;\n }\n });\n\n var tagName = everySectionHasTagName ? 'p' : sectionTagName;\n var firstChanged = undefined;\n post.walkMarkerableSections(range, function (section) {\n var changedSection = _this13.changeSectionTagName(section, tagName);\n firstChanged = firstChanged || changedSection;\n });\n\n if (firstChanged) {\n nextRange = firstChanged.headPosition().toRange();\n }\n this.setRange(nextRange);\n }\n }, {\n key: '_isSameSectionType',\n value: function _isSameSectionType(section, sectionTagName) {\n return section.isListItem ? section.parent.tagName === sectionTagName : section.tagName === sectionTagName;\n }\n\n /**\n * @param {Markerable} section\n * @private\n */\n }, {\n key: 'changeSectionTagName',\n value: function changeSectionTagName(section, newTagName) {\n (0, _mobiledocKitUtilsAssert['default'])('Cannot pass non-markerable section to `changeSectionTagName`', section.isMarkerable);\n\n if (isListSectionTagName(newTagName)) {\n return this._changeSectionToListItem(section, newTagName);\n } else if (section.isListItem) {\n return this._changeSectionFromListItem(section, newTagName);\n } else {\n section.tagName = newTagName;\n this._markDirty(section);\n return section;\n }\n }\n\n /**\n * Splits the item at the position given.\n * If the position is at the start or end of the item, the pre- or post-item\n * will contain a single empty (\"\") marker.\n * @param {ListItem} item\n * @param {Position} position\n * @return {Array} the pre-item and post-item on either side of the split\n * @private\n */\n }, {\n key: '_splitListItem',\n value: function _splitListItem(item, position) {\n var section = position.section;\n var offset = position.offset;\n\n (0, _mobiledocKitUtilsAssert['default'])('Cannot split list item at position that does not include item', item === section);\n\n item.splitMarkerAtOffset(offset);\n var prevMarker = item.markerBeforeOffset(offset);\n var preItem = this.builder.createListItem(),\n postItem = this.builder.createListItem();\n\n var currentItem = preItem;\n item.markers.forEach(function (marker) {\n currentItem.markers.append(marker.clone());\n if (marker === prevMarker) {\n currentItem = postItem;\n }\n });\n this._replaceSection(item, [preItem, postItem]);\n return [preItem, postItem];\n }\n\n /**\n * Splits the list at the position given.\n * @return {Array} pre-split list and post-split list, either of which could\n * be blank (0-item list) if the position is at the start or end of the list.\n *\n * Note: Contiguous list sections will be joined in the before_complete queue\n * of the postEditor.\n *\n * @private\n */\n }, {\n key: '_splitListAtPosition',\n value: function _splitListAtPosition(list, position) {\n (0, _mobiledocKitUtilsAssert['default'])('Cannot split list at position not in list', position.section.parent === list);\n\n var positionIsMiddle = !position.isHead() && !position.isTail();\n if (positionIsMiddle) {\n var item = position.section;\n\n var _splitListItem3 = // jshint ignore:line\n this._splitListItem(item, position);\n\n var _splitListItem32 = _slicedToArray(_splitListItem3, 2);\n\n var pre = _splitListItem32[0];\n var post = _splitListItem32[1];\n\n position = pre.tailPosition();\n }\n\n var preList = this.builder.createListSection(list.tagName);\n var postList = this.builder.createListSection(list.tagName);\n\n var preItem = position.section;\n var currentList = preList;\n list.items.forEach(function (item) {\n // If this item matches the start item and the position is at its start,\n // it should be appended to the postList instead of the preList\n if (item === preItem && position.isEqual(item.headPosition())) {\n currentList = postList;\n }\n currentList.items.append(item.clone());\n // If we just appended the preItem, append the remaining items to the postList\n if (item === preItem) {\n currentList = postList;\n }\n });\n\n this._replaceSection(list, [preList, postList]);\n return [preList, postList];\n }\n\n /**\n * @return Array of [prev, mid, next] lists. `prev` and `next` can\n * be blank, depending on the position of `item`. `mid` will always\n * be a 1-item list containing `item`. `prev` and `next` will be\n * removed in the before_complete queue if they are blank\n * (and still attached).\n *\n * @private\n */\n }, {\n key: '_splitListAtItem',\n value: function _splitListAtItem(list, item) {\n var _this14 = this;\n\n var next = list;\n var prev = this.builder.createListSection(next.tagName);\n var mid = this.builder.createListSection(next.tagName);\n\n var addToPrev = true;\n // must turn the LinkedList into an array so that we can remove items\n // as we iterate through it\n var items = next.items.toArray();\n items.forEach(function (i) {\n var listToAppend = undefined;\n if (i === item) {\n addToPrev = false;\n listToAppend = mid;\n } else if (addToPrev) {\n listToAppend = prev;\n } else {\n return; // break after iterating prev and mid parts of the list\n }\n listToAppend.join(i);\n _this14.removeSection(i);\n });\n var found = !addToPrev;\n (0, _mobiledocKitUtilsAssert['default'])('Cannot split list at item that is not present in the list', found);\n\n var collection = this.editor.post.sections;\n this.insertSectionBefore(collection, mid, next);\n this.insertSectionBefore(collection, prev, mid);\n\n // Remove possibly blank prev/next lists\n this.addCallback(CALLBACK_QUEUES.BEFORE_COMPLETE, function () {\n [prev, next].forEach(function (_list) {\n var isAttached = !!_list.parent;\n if (_list.isBlank && isAttached) {\n _this14.removeSection(_list);\n }\n });\n });\n\n return [prev, mid, next];\n }\n }, {\n key: '_changeSectionFromListItem',\n value: function _changeSectionFromListItem(section, newTagName) {\n (0, _mobiledocKitUtilsAssert['default'])('Must pass list item to `_changeSectionFromListItem`', section.isListItem);\n\n var listSection = section.parent;\n var markupSection = this.builder.createMarkupSection(newTagName);\n markupSection.join(section);\n\n var _splitListAtItem2 = this._splitListAtItem(listSection, section);\n\n var _splitListAtItem22 = _slicedToArray(_splitListAtItem2, 3);\n\n var prev = _splitListAtItem22[0];\n var mid = _splitListAtItem22[1];\n var next = _splitListAtItem22[2];\n // jshint ignore:line\n this.replaceSection(mid, markupSection);\n return markupSection;\n }\n }, {\n key: '_changeSectionToListItem',\n value: function _changeSectionToListItem(section, newTagName) {\n var isAlreadyCorrectListItem = section.isListItem && section.parent.tagName === newTagName;\n\n if (isAlreadyCorrectListItem) {\n return section;\n }\n\n var listSection = this.builder.createListSection(newTagName);\n listSection.join(section);\n\n var sectionToReplace = undefined;\n if (section.isListItem) {\n var _splitListAtItem3 = this._splitListAtItem(section.parent, section);\n\n var _splitListAtItem32 = _slicedToArray(_splitListAtItem3, 3);\n\n var prev = _splitListAtItem32[0];\n var mid = _splitListAtItem32[1];\n var next = _splitListAtItem32[2];\n // jshint ignore:line\n sectionToReplace = mid;\n } else {\n sectionToReplace = section;\n }\n this.replaceSection(sectionToReplace, listSection);\n return listSection;\n }\n\n /**\n * Insert a given section before another one, updating the post abstract\n * and the rendered UI.\n *\n * Usage:\n * ```\n * let markerRange = editor.range;\n * let sectionWithCursor = markerRange.headMarker.section;\n * let section = editor.builder.createCardSection('my-image');\n * let collection = sectionWithCursor.parent.sections;\n * editor.run((postEditor) => {\n * postEditor.insertSectionBefore(collection, section, sectionWithCursor);\n * });\n * ```\n * @param {LinkedList} collection The list of sections to insert into\n * @param {Object} section The new section\n * @param {Object} beforeSection Optional The section \"before\" is relative to,\n * if falsy the new section will be appended to the collection\n * @public\n */\n }, {\n key: 'insertSectionBefore',\n value: function insertSectionBefore(collection, section, beforeSection) {\n collection.insertBefore(section, beforeSection);\n this._markDirty(section.parent);\n }\n\n /**\n * Insert the given section after the current active section, or, if no\n * section is active, at the end of the document.\n * @param {Section} section\n * @public\n */\n }, {\n key: 'insertSection',\n value: function insertSection(section) {\n var activeSection = this.editor.activeSection;\n var nextSection = activeSection && activeSection.next;\n\n var collection = this.editor.post.sections;\n this.insertSectionBefore(collection, section, nextSection);\n }\n\n /**\n * Insert the given section at the end of the document.\n * @param {Section} section\n * @public\n */\n }, {\n key: 'insertSectionAtEnd',\n value: function insertSectionAtEnd(section) {\n this.insertSectionBefore(this.editor.post.sections, section, null);\n }\n\n /**\n * Insert the `post` at the given position in the editor's post.\n * @param {Position} position\n * @param {Post} post\n * @private\n */\n }, {\n key: 'insertPost',\n value: function insertPost(position, newPost) {\n var post = this.editor.post;\n var inserter = new _mobiledocKitEditorPostPostInserter['default'](this, post);\n var nextPosition = inserter.insert(position, newPost);\n return nextPosition;\n }\n\n /**\n * Remove a given section from the post abstract and the rendered UI.\n *\n * Usage:\n * ```\n * let { range } = editor;\n * let sectionWithCursor = range.head.section;\n * editor.run((postEditor) => {\n * postEditor.removeSection(sectionWithCursor);\n * });\n * ```\n * @param {Object} section The section to remove\n * @public\n */\n }, {\n key: 'removeSection',\n value: function removeSection(section) {\n var parent = section.parent;\n this._scheduleForRemoval(section);\n parent.sections.remove(section);\n\n if (parent.isListSection) {\n this._scheduleListRemovalIfEmpty(parent);\n }\n }\n }, {\n key: 'removeAllSections',\n value: function removeAllSections() {\n var _this15 = this;\n\n this.editor.post.sections.toArray().forEach(function (section) {\n _this15.removeSection(section);\n });\n }\n }, {\n key: 'migrateSectionsFromPost',\n value: function migrateSectionsFromPost(post) {\n var _this16 = this;\n\n post.sections.toArray().forEach(function (section) {\n post.sections.remove(section);\n _this16.insertSectionBefore(_this16.editor.post.sections, section, null);\n });\n }\n }, {\n key: '_scheduleListRemovalIfEmpty',\n value: function _scheduleListRemovalIfEmpty(listSection) {\n var _this17 = this;\n\n this.addCallback(CALLBACK_QUEUES.BEFORE_COMPLETE, function () {\n // if the list is attached and blank after we do other rendering stuff,\n // remove it\n var isAttached = !!listSection.parent;\n if (isAttached && listSection.isBlank) {\n _this17.removeSection(listSection);\n }\n });\n }\n\n /**\n * A method for adding work the deferred queue\n *\n * @param {Function} callback to run during completion\n * @param {Boolean} [once=false] Whether to only schedule the callback once.\n * @public\n */\n }, {\n key: 'schedule',\n value: function schedule(callback) {\n var once = arguments.length <= 1 || arguments[1] === undefined ? false : arguments[1];\n\n (0, _mobiledocKitUtilsAssert['default'])('Work can only be scheduled before a post edit has completed', !this._didComplete);\n if (once) {\n this.addCallbackOnce(CALLBACK_QUEUES.COMPLETE, callback);\n } else {\n this.addCallback(CALLBACK_QUEUES.COMPLETE, callback);\n }\n }\n\n /**\n * A method for adding work the deferred queue. The callback will only\n * be added to the queue once, even if `scheduleOnce` is called multiple times.\n * The function cannot be an anonymous function.\n *\n * @param {Function} callback to run during completion\n * @public\n */\n }, {\n key: 'scheduleOnce',\n value: function scheduleOnce(callback) {\n this.schedule(callback, true);\n }\n\n /**\n * Add a rerender job to the queue\n *\n * @public\n */\n }, {\n key: 'scheduleRerender',\n value: function scheduleRerender() {\n this.scheduleOnce(this._rerender);\n }\n\n /**\n * Schedule a notification that the post has been changed.\n * The notification will result in the editor firing its `postDidChange`\n * hook after the postEditor completes its work (at the end of {@link Editor#run}).\n *\n * @public\n */\n }, {\n key: 'scheduleDidUpdate',\n value: function scheduleDidUpdate() {\n this.scheduleOnce(this._postDidChange);\n }\n }, {\n key: 'scheduleAfterRender',\n value: function scheduleAfterRender(callback) {\n var once = arguments.length <= 1 || arguments[1] === undefined ? false : arguments[1];\n\n if (once) {\n this.addCallbackOnce(CALLBACK_QUEUES.AFTER_COMPLETE, callback);\n } else {\n this.addCallback(CALLBACK_QUEUES.AFTER_COMPLETE, callback);\n }\n }\n\n /**\n * Flush any work on the queue. {@link Editor#run} calls this method; it\n * should not be called directly.\n *\n * @private\n */\n }, {\n key: 'complete',\n value: function complete() {\n (0, _mobiledocKitUtilsAssert['default'])('Post editing can only be completed once', !this._didComplete);\n\n this.runCallbacks(CALLBACK_QUEUES.BEFORE_COMPLETE);\n this._didComplete = true;\n this.runCallbacks(CALLBACK_QUEUES.COMPLETE);\n this.runCallbacks(CALLBACK_QUEUES.AFTER_COMPLETE);\n }\n }, {\n key: 'undoLastChange',\n value: function undoLastChange() {\n this.editor._editHistory.stepBackward(this);\n }\n }, {\n key: 'redoLastChange',\n value: function redoLastChange() {\n this.editor._editHistory.stepForward(this);\n }\n }, {\n key: 'cancelSnapshot',\n value: function cancelSnapshot() {\n this._shouldCancelSnapshot = true;\n }\n }]);\n\n return PostEditor;\n })();\n\n exports['default'] = PostEditor;\n});","define('mobiledoc-kit/editor/post/post-inserter', ['exports', 'mobiledoc-kit/utils/assert', 'mobiledoc-kit/models/types'], function (exports, _mobiledocKitUtilsAssert, _mobiledocKitModelsTypes) {\n 'use strict';\n\n var _slicedToArray = (function () { function sliceIterator(arr, i) { var _arr = []; var _n = true; var _d = false; var _e = undefined; try { for (var _i = arr[Symbol.iterator](), _s; !(_n = (_s = _i.next()).done); _n = true) { _arr.push(_s.value); if (i && _arr.length === i) break; } } catch (err) { _d = true; _e = err; } finally { try { if (!_n && _i['return']) _i['return'](); } finally { if (_d) throw _e; } } return _arr; } return function (arr, i) { if (Array.isArray(arr)) { return arr; } else if (Symbol.iterator in Object(arr)) { return sliceIterator(arr, i); } else { throw new TypeError('Invalid attempt to destructure non-iterable instance'); } }; })();\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n var MARKERABLE = 'markerable',\n NESTED_MARKERABLE = 'nested_markerable',\n NON_MARKERABLE = 'non_markerable';\n\n var Visitor = (function () {\n function Visitor(inserter, cursorPosition) {\n _classCallCheck(this, Visitor);\n\n var postEditor = inserter.postEditor;\n var post = inserter.post;\n\n this.postEditor = postEditor;\n this._post = post;\n this.cursorPosition = cursorPosition;\n this.builder = this.postEditor.builder;\n\n this._hasInsertedFirstLeafSection = false;\n }\n\n _createClass(Visitor, [{\n key: 'visit',\n value: function visit(node) {\n var method = node.type;\n (0, _mobiledocKitUtilsAssert['default'])('Cannot visit node of type ' + node.type, !!this[method]);\n this[method](node);\n }\n }, {\n key: '_canMergeSection',\n value: function _canMergeSection(section) {\n if (this._hasInsertedFirstLeafSection) {\n return false;\n } else {\n return this._isMarkerable && section.isMarkerable;\n }\n }\n }, {\n key: _mobiledocKitModelsTypes.POST_TYPE,\n value: function value(node) {\n var _this = this;\n\n if (this.cursorSection.isBlank && !this._isNested) {\n // replace blank section with entire post\n var newSections = node.sections.map(function (s) {\n return s.clone();\n });\n this._replaceSection(this.cursorSection, newSections);\n } else {\n node.sections.forEach(function (section) {\n return _this.visit(section);\n });\n }\n }\n }, {\n key: _mobiledocKitModelsTypes.MARKUP_SECTION_TYPE,\n value: function value(node) {\n this[MARKERABLE](node);\n }\n }, {\n key: _mobiledocKitModelsTypes.LIST_SECTION_TYPE,\n value: function value(node) {\n var _this2 = this;\n\n var hasNext = !!node.next;\n node.items.forEach(function (item) {\n return _this2.visit(item);\n });\n\n if (this._isNested && hasNext) {\n this._breakNestedAtCursor();\n }\n }\n }, {\n key: _mobiledocKitModelsTypes.LIST_ITEM_TYPE,\n value: function value(node) {\n this[NESTED_MARKERABLE](node);\n }\n }, {\n key: _mobiledocKitModelsTypes.CARD_TYPE,\n value: function value(node) {\n this[NON_MARKERABLE](node);\n }\n }, {\n key: _mobiledocKitModelsTypes.IMAGE_SECTION_TYPE,\n value: function value(node) {\n this[NON_MARKERABLE](node);\n }\n }, {\n key: NON_MARKERABLE,\n value: function value(section) {\n if (this._isNested) {\n this._breakNestedAtCursor();\n } else if (!this.cursorSection.isBlank) {\n this._breakAtCursor();\n }\n\n this._insertLeafSection(section);\n }\n }, {\n key: MARKERABLE,\n value: function value(section) {\n if (this._canMergeSection(section)) {\n this._mergeSection(section);\n } else if (this._isNested && this._isMarkerable) {\n // If we are attaching a markerable section to a list item,\n // insert a linebreak then merge the section onto the resulting blank list item\n this._breakAtCursor();\n\n // Advance the cursor to the head of the blank list item\n var nextPosition = this.cursorSection.next.headPosition();\n this.cursorPosition = nextPosition;\n\n // Merge this section onto the list item\n this._mergeSection(section);\n } else {\n this._breakAtCursor();\n this._insertLeafSection(section);\n }\n }\n }, {\n key: NESTED_MARKERABLE,\n value: function value(section) {\n if (this._canMergeSection(section)) {\n this._mergeSection(section);\n return;\n }\n\n section = this._isNested ? section : this._wrapNestedSection(section);\n this._breakAtCursor();\n this._insertLeafSection(section);\n }\n\n // break out of a nested cursor position\n }, {\n key: '_breakNestedAtCursor',\n value: function _breakNestedAtCursor() {\n (0, _mobiledocKitUtilsAssert['default'])('Cannot call _breakNestedAtCursor if not nested', this._isNested);\n\n var parent = this.cursorSection.parent;\n var cursorAtEndOfList = this.cursorPosition.isEqual(parent.tailPosition());\n\n if (cursorAtEndOfList) {\n var blank = this.builder.createMarkupSection();\n this._insertSectionAfter(blank, parent);\n } else {\n var _breakListAtCursor2 = this._breakListAtCursor();\n\n var _breakListAtCursor22 = _slicedToArray(_breakListAtCursor2, 3);\n\n var pre = _breakListAtCursor22[0];\n var blank = _breakListAtCursor22[1];\n var post = _breakListAtCursor22[2];\n // jshint ignore:line\n this.cursorPosition = blank.tailPosition();\n }\n }\n }, {\n key: '_breakListAtCursor',\n value: function _breakListAtCursor() {\n (0, _mobiledocKitUtilsAssert['default'])('Cannot _splitParentSection if cursor position is not nested', this._isNested);\n\n var list = this.cursorSection.parent,\n position = this.cursorPosition,\n blank = this.builder.createMarkupSection();\n\n var _postEditor$_splitListAtPosition = this.postEditor._splitListAtPosition(list, position);\n\n var _postEditor$_splitListAtPosition2 = _slicedToArray(_postEditor$_splitListAtPosition, 2);\n\n var pre = _postEditor$_splitListAtPosition2[0];\n var post = _postEditor$_splitListAtPosition2[1];\n\n var collection = this._post.sections,\n reference = post;\n this.postEditor.insertSectionBefore(collection, blank, reference);\n return [pre, blank, post];\n }\n }, {\n key: '_wrapNestedSection',\n value: function _wrapNestedSection(section) {\n var tagName = section.parent.tagName;\n var parent = this.builder.createListSection(tagName);\n parent.items.append(section.clone());\n return parent;\n }\n }, {\n key: '_mergeSection',\n value: function _mergeSection(section) {\n (0, _mobiledocKitUtilsAssert['default'])('Can only merge markerable sections', this._isMarkerable && section.isMarkerable);\n this._hasInsertedFirstLeafSection = true;\n\n var markers = section.markers.map(function (m) {\n return m.clone();\n });\n var position = this.postEditor.insertMarkers(this.cursorPosition, markers);\n\n this.cursorPosition = position;\n }\n\n // Can be called to add a line break when in a nested section or a parent\n // section.\n }, {\n key: '_breakAtCursor',\n value: function _breakAtCursor() {\n if (this.cursorSection.isBlank) {\n return;\n } else if (this._isMarkerable) {\n this._breakMarkerableAtCursor();\n } else {\n this._breakNonMarkerableAtCursor();\n }\n }\n\n // Inserts a blank section before/after the cursor,\n // depending on cursor position.\n }, {\n key: '_breakNonMarkerableAtCursor',\n value: function _breakNonMarkerableAtCursor() {\n var collection = this._post.sections,\n blank = this.builder.createMarkupSection(),\n reference = this.cursorPosition.isHead() ? this.cursorSection : this.cursorSection.next;\n this.postEditor.insertSectionBefore(collection, blank, reference);\n this.cursorPosition = blank.tailPosition();\n }\n }, {\n key: '_breakMarkerableAtCursor',\n value: function _breakMarkerableAtCursor() {\n var _postEditor$splitSection = // jshint ignore:line\n this.postEditor.splitSection(this.cursorPosition);\n\n var _postEditor$splitSection2 = _slicedToArray(_postEditor$splitSection, 2);\n\n var pre = _postEditor$splitSection2[0];\n var post = _postEditor$splitSection2[1];\n\n this.cursorPosition = pre.tailPosition();\n }\n }, {\n key: '_replaceSection',\n value: function _replaceSection(section, newSections) {\n var _this3 = this;\n\n (0, _mobiledocKitUtilsAssert['default'])('Cannot replace section that does not have parent.sections', section.parent && section.parent.sections);\n (0, _mobiledocKitUtilsAssert['default'])('Must pass enumerable to _replaceSection', !!newSections.forEach);\n\n var collection = section.parent.sections;\n var reference = section.next;\n this.postEditor.removeSection(section);\n newSections.forEach(function (section) {\n _this3.postEditor.insertSectionBefore(collection, section, reference);\n });\n var lastSection = newSections[newSections.length - 1];\n\n this.cursorPosition = lastSection.tailPosition();\n }\n }, {\n key: '_insertSectionBefore',\n value: function _insertSectionBefore(section, reference) {\n var collection = this.cursorSection.parent.sections;\n this.postEditor.insertSectionBefore(collection, section, reference);\n\n this.cursorPosition = section.tailPosition();\n }\n\n // Insert a section after the parent section.\n // E.g., add a markup section after a list section\n }, {\n key: '_insertSectionAfter',\n value: function _insertSectionAfter(section, parent) {\n (0, _mobiledocKitUtilsAssert['default'])('Cannot _insertSectionAfter nested section', !parent.isNested);\n var reference = parent.next;\n var collection = this._post.sections;\n this.postEditor.insertSectionBefore(collection, section, reference);\n this.cursorPosition = section.tailPosition();\n }\n }, {\n key: '_insertLeafSection',\n value: function _insertLeafSection(section) {\n (0, _mobiledocKitUtilsAssert['default'])('Can only _insertLeafSection when cursor is at end of section', this.cursorPosition.isTail());\n\n this._hasInsertedFirstLeafSection = true;\n section = section.clone();\n\n if (this.cursorSection.isBlank) {\n (0, _mobiledocKitUtilsAssert['default'])('Cannot insert leaf non-markerable section when cursor is nested', !(section.isMarkerable && this._isNested));\n this._replaceSection(this.cursorSection, [section]);\n } else if (this.cursorSection.next && this.cursorSection.next.isBlank) {\n this._replaceSection(this.cursorSection.next, [section]);\n } else {\n var reference = this.cursorSection.next;\n this._insertSectionBefore(section, reference);\n }\n }\n }, {\n key: 'cursorPosition',\n get: function get() {\n return this._cursorPosition;\n },\n set: function set(position) {\n this._cursorPosition = position;\n this.postEditor.setRange(position);\n }\n }, {\n key: '_isMarkerable',\n get: function get() {\n return this.cursorSection.isMarkerable;\n }\n }, {\n key: 'cursorSection',\n get: function get() {\n return this.cursorPosition.section;\n }\n }, {\n key: 'cursorOffset',\n get: function get() {\n return this.cursorPosition.offset;\n }\n }, {\n key: '_isNested',\n get: function get() {\n return this.cursorSection.isNested;\n }\n }]);\n\n return Visitor;\n })();\n\n var Inserter = (function () {\n function Inserter(postEditor, post) {\n _classCallCheck(this, Inserter);\n\n this.postEditor = postEditor;\n this.post = post;\n }\n\n _createClass(Inserter, [{\n key: 'insert',\n value: function insert(cursorPosition, newPost) {\n var visitor = new Visitor(this, cursorPosition);\n visitor.visit(newPost);\n return visitor.cursorPosition;\n }\n }]);\n\n return Inserter;\n })();\n\n exports['default'] = Inserter;\n});","define(\"mobiledoc-kit/editor/selection-change-observer\", [\"exports\"], function (exports) {\n \"use strict\";\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if (\"value\" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError(\"Cannot call a class as a function\"); } }\n\n var instance = undefined;\n\n var SelectionChangeObserver = (function () {\n function SelectionChangeObserver() {\n _classCallCheck(this, SelectionChangeObserver);\n\n this.started = false;\n this.listeners = [];\n this.selection = {};\n }\n\n _createClass(SelectionChangeObserver, [{\n key: \"addListener\",\n value: function addListener(listener) {\n if (this.listeners.indexOf(listener) === -1) {\n this.listeners.push(listener);\n this.start();\n }\n }\n }, {\n key: \"removeListener\",\n value: function removeListener(listener) {\n var index = this.listeners.indexOf(listener);\n if (index !== -1) {\n this.listeners.splice(index, 1);\n if (this.listeners.length === 0) {\n this.stop();\n }\n }\n }\n }, {\n key: \"start\",\n value: function start() {\n if (this.started) {\n return;\n }\n this.started = true;\n\n this.poll();\n }\n }, {\n key: \"stop\",\n value: function stop() {\n this.started = false;\n this.selection = {};\n }\n }, {\n key: \"notifyListeners\",\n value: function notifyListeners() /* newSelection, prevSelection */{\n var _arguments = arguments;\n\n this.listeners.forEach(function (listener) {\n listener.selectionDidChange.apply(listener, _arguments);\n });\n }\n }, {\n key: \"destroy\",\n value: function destroy() {\n this.stop();\n this.listeners = [];\n }\n }, {\n key: \"getSelection\",\n value: function getSelection() {\n var selection = window.getSelection();\n var anchorNode = selection.anchorNode;\n var focusNode = selection.focusNode;\n var anchorOffset = selection.anchorOffset;\n var focusOffset = selection.focusOffset;\n\n return { anchorNode: anchorNode, focusNode: focusNode, anchorOffset: anchorOffset, focusOffset: focusOffset };\n }\n }, {\n key: \"poll\",\n value: function poll() {\n var _this = this;\n\n if (this.started) {\n this.update();\n this.runNext(function () {\n return _this.poll();\n });\n }\n }\n }, {\n key: \"runNext\",\n value: function runNext(fn) {\n window.requestAnimationFrame(fn);\n }\n }, {\n key: \"update\",\n value: function update() {\n var prevSelection = this.selection;\n var curSelection = this.getSelection();\n if (!this.selectionIsEqual(prevSelection, curSelection)) {\n this.selection = curSelection;\n this.notifyListeners(curSelection, prevSelection);\n }\n }\n }, {\n key: \"selectionIsEqual\",\n value: function selectionIsEqual(s1, s2) {\n return s1.anchorNode === s2.anchorNode && s1.anchorOffset === s2.anchorOffset && s1.focusNode === s2.focusNode && s1.focusOffset === s2.focusOffset;\n }\n }], [{\n key: \"getInstance\",\n value: function getInstance() {\n if (!instance) {\n instance = new SelectionChangeObserver();\n }\n return instance;\n }\n }, {\n key: \"addListener\",\n value: function addListener(listener) {\n SelectionChangeObserver.getInstance().addListener(listener);\n }\n }, {\n key: \"removeListener\",\n value: function removeListener(listener) {\n SelectionChangeObserver.getInstance().removeListener(listener);\n }\n }]);\n\n return SelectionChangeObserver;\n })();\n\n exports[\"default\"] = SelectionChangeObserver;\n});","define('mobiledoc-kit/editor/selection-manager', ['exports', 'mobiledoc-kit/editor/selection-change-observer'], function (exports, _mobiledocKitEditorSelectionChangeObserver) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n var SelectionManager = (function () {\n function SelectionManager(editor, callback) {\n _classCallCheck(this, SelectionManager);\n\n this.editor = editor;\n this.callback = callback;\n this.started = false;\n }\n\n _createClass(SelectionManager, [{\n key: 'start',\n value: function start() {\n if (this.started) {\n return;\n }\n\n _mobiledocKitEditorSelectionChangeObserver['default'].addListener(this);\n this.started = true;\n }\n }, {\n key: 'stop',\n value: function stop() {\n this.started = false;\n _mobiledocKitEditorSelectionChangeObserver['default'].removeListener(this);\n }\n }, {\n key: 'destroy',\n value: function destroy() {\n this.stop();\n }\n }, {\n key: 'selectionDidChange',\n value: function selectionDidChange() {\n if (this.started) {\n this.callback.apply(this, arguments);\n }\n }\n }]);\n\n return SelectionManager;\n })();\n\n exports['default'] = SelectionManager;\n});","define('mobiledoc-kit/editor/text-input-handler', ['exports', 'mobiledoc-kit/utils/string-utils', 'mobiledoc-kit/utils/assert', 'mobiledoc-kit/utils/deprecate'], function (exports, _mobiledocKitUtilsStringUtils, _mobiledocKitUtilsAssert, _mobiledocKitUtilsDeprecate) {\n 'use strict';\n\n var _slicedToArray = (function () { function sliceIterator(arr, i) { var _arr = []; var _n = true; var _d = false; var _e = undefined; try { for (var _i = arr[Symbol.iterator](), _s; !(_n = (_s = _i.next()).done); _n = true) { _arr.push(_s.value); if (i && _arr.length === i) break; } } catch (err) { _d = true; _e = err; } finally { try { if (!_n && _i['return']) _i['return'](); } finally { if (_d) throw _e; } } return _arr; } return function (arr, i) { if (Array.isArray(arr)) { return arr; } else if (Symbol.iterator in Object(arr)) { return sliceIterator(arr, i); } else { throw new TypeError('Invalid attempt to destructure non-iterable instance'); } }; })();\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n var TextInputHandler = (function () {\n function TextInputHandler(editor) {\n _classCallCheck(this, TextInputHandler);\n\n this.editor = editor;\n this._handlers = [];\n }\n\n _createClass(TextInputHandler, [{\n key: 'register',\n value: function register(handler) {\n (0, _mobiledocKitUtilsAssert['default'])('Input Handler is not valid', this._validateHandler(handler));\n this._handlers.push(handler);\n }\n }, {\n key: 'unregister',\n value: function unregister(name) {\n var handlers = this._handlers;\n for (var i = 0; i < handlers.length; i++) {\n if (handlers[i].name === name) {\n handlers.splice(i, 1);\n }\n }\n }\n }, {\n key: 'handle',\n value: function handle(string) {\n var editor = this.editor;\n\n editor.insertText(string);\n\n var matchedHandler = this._findHandler();\n if (matchedHandler) {\n var _matchedHandler = _slicedToArray(matchedHandler, 2);\n\n var handler = _matchedHandler[0];\n var matches = _matchedHandler[1];\n\n handler.run(editor, matches);\n }\n }\n }, {\n key: '_findHandler',\n value: function _findHandler() {\n var _editor$range = this.editor.range;\n var head = _editor$range.head;\n var section = _editor$range.head.section;\n\n var preText = section.textUntil(head);\n\n for (var i = 0; i < this._handlers.length; i++) {\n var handler = this._handlers[i];\n var text = handler.text;\n var match = handler.match;\n\n if (text && (0, _mobiledocKitUtilsStringUtils.endsWith)(preText, text)) {\n return [handler, [text]];\n } else if (match && match.test(preText)) {\n return [handler, match.exec(preText)];\n }\n }\n }\n }, {\n key: '_validateHandler',\n value: function _validateHandler(handler) {\n (0, _mobiledocKitUtilsDeprecate['default'])('Registered input handlers require a \"name\" property so that they can be unregistered', !!handler.name);\n return !!handler.run && ( // has `run`\n !!handler.text || !!handler.match) && // and `text` or `match`\n !(!!handler.text && !!handler.match); // not both `text` and `match`\n }\n }, {\n key: 'destroy',\n value: function destroy() {\n this._handlers = [];\n }\n }]);\n\n return TextInputHandler;\n })();\n\n exports['default'] = TextInputHandler;\n});","define('mobiledoc-kit/editor/text-input-handlers', ['exports'], function (exports) {\n /**\n * Convert section at the editor's cursor position into a list.\n * Does nothing if the cursor position is not at the start of the section,\n * or if the section is already a list item.\n *\n * @param {Editor} editor\n * @param {String} listTagName (\"ul\" or \"ol\")\n * @public\n */\n 'use strict';\n\n exports.replaceWithListSection = replaceWithListSection;\n exports.replaceWithHeaderSection = replaceWithHeaderSection;\n\n function replaceWithListSection(editor, listTagName) {\n var _editor$range = editor.range;\n var head = _editor$range.head;\n var section = _editor$range.head.section;\n\n // Skip if cursor is not at end of section\n if (!head.isTail()) {\n return;\n }\n\n if (section.isListItem) {\n return;\n }\n\n editor.run(function (postEditor) {\n var builder = postEditor.builder;\n\n var item = builder.createListItem();\n var listSection = builder.createListSection(listTagName, [item]);\n\n postEditor.replaceSection(section, listSection);\n postEditor.setRange(listSection.headPosition());\n });\n }\n\n /**\n * Convert section at the editor's cursor position into a header section.\n * Does nothing if the cursor position is not at the start of the section.\n *\n * @param {Editor} editor\n * @param {String} headingTagName ('h1', 'h2', 'h3', 'h4', 'h5', 'h6')\n * @public\n */\n\n function replaceWithHeaderSection(editor, headingTagName) {\n var _editor$range2 = editor.range;\n var head = _editor$range2.head;\n var section = _editor$range2.head.section;\n\n // Skip if cursor is not at end of section\n if (!head.isTail()) {\n return;\n }\n\n editor.run(function (postEditor) {\n var builder = postEditor.builder;\n\n var newSection = builder.createMarkupSection(headingTagName);\n postEditor.replaceSection(section, newSection);\n postEditor.setRange(newSection.headPosition());\n });\n }\n\n var DEFAULT_TEXT_INPUT_HANDLERS = [{\n name: 'ul',\n // \"* \" -> ul\n match: /^\\* $/,\n run: function run(editor) {\n replaceWithListSection(editor, 'ul');\n }\n }, {\n name: 'ol',\n // \"1\" -> ol, \"1.\" -> ol\n match: /^1\\.? $/,\n run: function run(editor) {\n replaceWithListSection(editor, 'ol');\n }\n }, {\n name: 'heading',\n /*\n * \"# \" -> h1\n * \"## \" -> h2\n * \"### \" -> h3\n * \"#### \" -> h4\n * \"##### \" -> h5\n * \"###### \" -> h6\n */\n match: /^(#{1,6}) $/,\n run: function run(editor, matches) {\n var capture = matches[1];\n var headingTag = 'h' + capture.length;\n replaceWithHeaderSection(editor, headingTag);\n }\n }];\n exports.DEFAULT_TEXT_INPUT_HANDLERS = DEFAULT_TEXT_INPUT_HANDLERS;\n});","define('mobiledoc-kit/editor/ui', ['exports'], function (exports) {\n /**\n * @module UI\n */\n\n /**\n * @callback promptCallback\n * @param {String} url The URL to pass back to the editor for linking\n * to the selected text.\n */\n\n /**\n * @callback showPrompt\n * @param {String} message The text of the prompt.\n * @param {String} defaultValue The initial URL to display in the prompt.\n * @param {module:UI~promptCallback} callback Once your handler has accepted a URL,\n * it should pass it to `callback` so that the editor may link the\n * selected text.\n */\n\n /**\n * Exposes the core behavior for linking and unlinking text, and allows for\n * customization of the URL input handler.\n * @param {Editor} editor An editor instance to operate on. If a range is selected,\n * either prompt for a URL and add a link or un-link the\n * currently linked text.\n * @param {module:UI~showPrompt} [showPrompt] An optional custom input handler. Defaults\n * to using `window.prompt`.\n * @example\n * let myPrompt = (message, defaultURL, promptCallback) => {\n * let url = window.prompt(\"Overriding the defaults\", \"http://placekitten.com\");\n * promptCallback(url);\n * };\n *\n * editor.registerKeyCommand({\n * str: \"META+K\",\n * run(editor) {\n * toggleLink(editor, myPrompt);\n * }\n * });\n * @public\n */\n\n 'use strict';\n\n exports.toggleLink = toggleLink;\n var defaultShowPrompt = function defaultShowPrompt(message, defaultValue, callback) {\n return callback(window.prompt(message, defaultValue));\n };\n\n function toggleLink(editor) {\n var showPrompt = arguments.length <= 1 || arguments[1] === undefined ? defaultShowPrompt : arguments[1];\n\n if (editor.range.isCollapsed) {\n return;\n }\n\n var selectedText = editor.cursor.selectedText();\n var defaultUrl = '';\n if (selectedText.indexOf('http') !== -1) {\n defaultUrl = selectedText;\n }\n\n var range = editor.range;\n\n var hasLink = editor.detectMarkupInRange(range, 'a');\n\n if (hasLink) {\n editor.run(function (postEditor) {\n return postEditor.toggleMarkup('a');\n });\n } else {\n showPrompt('Enter a URL', defaultUrl, function (url) {\n if (!url) {\n return;\n }\n\n editor.run(function (postEditor) {\n var markup = postEditor.builder.createMarkup('a', { href: url });\n postEditor.toggleMarkup(markup);\n });\n });\n }\n }\n});","define('mobiledoc-kit', ['exports', 'mobiledoc-kit/editor/editor', 'mobiledoc-kit/editor/ui', 'mobiledoc-kit/cards/image', 'mobiledoc-kit/utils/cursor/range', 'mobiledoc-kit/utils/cursor/position', 'mobiledoc-kit/utils/mobiledoc-error', 'mobiledoc-kit/version'], function (exports, _mobiledocKitEditorEditor, _mobiledocKitEditorUi, _mobiledocKitCardsImage, _mobiledocKitUtilsCursorRange, _mobiledocKitUtilsCursorPosition, _mobiledocKitUtilsMobiledocError, _mobiledocKitVersion) {\n 'use strict';\n\n exports.registerGlobal = registerGlobal;\n\n var Mobiledoc = {\n Editor: _mobiledocKitEditorEditor['default'],\n UI: _mobiledocKitEditorUi,\n ImageCard: _mobiledocKitCardsImage['default'],\n Range: _mobiledocKitUtilsCursorRange['default'],\n Position: _mobiledocKitUtilsCursorPosition['default'],\n Error: _mobiledocKitUtilsMobiledocError['default'],\n VERSION: _mobiledocKitVersion['default']\n };\n\n function registerGlobal(global) {\n global.Mobiledoc = Mobiledoc;\n }\n\n exports.Editor = _mobiledocKitEditorEditor['default'];\n exports.UI = _mobiledocKitEditorUi;\n exports.Range = _mobiledocKitUtilsCursorRange['default'];\n exports.Position = _mobiledocKitUtilsCursorPosition['default'];\n exports['default'] = Mobiledoc;\n});","define('mobiledoc-kit/models/_markerable', ['exports', 'mobiledoc-kit/utils/array-utils', 'mobiledoc-kit/utils/set', 'mobiledoc-kit/utils/linked-list', 'mobiledoc-kit/models/_section', 'mobiledoc-kit/utils/assert'], function (exports, _mobiledocKitUtilsArrayUtils, _mobiledocKitUtilsSet, _mobiledocKitUtilsLinkedList, _mobiledocKitModels_section, _mobiledocKitUtilsAssert) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n var _get = function get(_x4, _x5, _x6) { var _again = true; _function: while (_again) { var object = _x4, property = _x5, receiver = _x6; _again = false; if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { _x4 = parent; _x5 = property; _x6 = receiver; _again = true; desc = parent = undefined; continue _function; } } else if ('value' in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } } };\n\n function _toConsumableArray(arr) { if (Array.isArray(arr)) { for (var i = 0, arr2 = Array(arr.length); i < arr.length; i++) arr2[i] = arr[i]; return arr2; } else { return Array.from(arr); } }\n\n function _toArray(arr) { return Array.isArray(arr) ? arr : Array.from(arr); }\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n function _inherits(subClass, superClass) { if (typeof superClass !== 'function' && superClass !== null) { throw new TypeError('Super expression must either be null or a function, not ' + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }\n\n var Markerable = (function (_Section) {\n _inherits(Markerable, _Section);\n\n function Markerable(type, tagName) {\n var _this = this;\n\n var markers = arguments.length <= 2 || arguments[2] === undefined ? [] : arguments[2];\n\n _classCallCheck(this, Markerable);\n\n _get(Object.getPrototypeOf(Markerable.prototype), 'constructor', this).call(this, type);\n this.isMarkerable = true;\n this.tagName = tagName;\n this.markers = new _mobiledocKitUtilsLinkedList['default']({\n adoptItem: function adoptItem(m) {\n (0, _mobiledocKitUtilsAssert['default'])('Can only insert markers and atoms into markerable (was: ' + m.type + ')', m.isMarker || m.isAtom);\n m.section = m.parent = _this;\n },\n freeItem: function freeItem(m) {\n return m.section = m.parent = null;\n }\n });\n\n markers.forEach(function (m) {\n return _this.markers.append(m);\n });\n }\n\n _createClass(Markerable, [{\n key: 'canJoin',\n value: function canJoin(other) {\n return other.isMarkerable && other.type === this.type && other.tagName === this.tagName;\n }\n }, {\n key: 'clone',\n value: function clone() {\n var newMarkers = this.markers.map(function (m) {\n return m.clone();\n });\n return this.builder.createMarkerableSection(this.type, this.tagName, newMarkers);\n }\n }, {\n key: 'textUntil',\n value: function textUntil(position) {\n (0, _mobiledocKitUtilsAssert['default'])('Cannot get textUntil for a position not in this section', position.section === this);\n var marker = position.marker;\n var offsetInMarker = position.offsetInMarker;\n\n var text = '';\n var currentMarker = this.markers.head;\n while (currentMarker) {\n if (currentMarker === marker) {\n text += currentMarker.textUntil(offsetInMarker);\n break;\n } else {\n text += currentMarker.text;\n currentMarker = currentMarker.next;\n }\n }\n return text;\n }\n\n /**\n * @param {Marker}\n * @param {Number} markerOffset The offset relative to the start of the marker\n *\n * @return {Number} The offset relative to the start of this section\n */\n }, {\n key: 'offsetOfMarker',\n value: function offsetOfMarker(marker) {\n var markerOffset = arguments.length <= 1 || arguments[1] === undefined ? 0 : arguments[1];\n\n (0, _mobiledocKitUtilsAssert['default'])('Cannot get offsetOfMarker for marker that is not child of this', marker.section === this);\n\n // FIXME it is possible, when we get a cursor position before having finished reparsing,\n // for markerOffset to be > marker.length. We shouldn't rely on this functionality.\n\n var offset = 0;\n var currentMarker = this.markers.head;\n while (currentMarker && currentMarker !== marker.next) {\n var _length = currentMarker === marker ? markerOffset : currentMarker.length;\n offset += _length;\n currentMarker = currentMarker.next;\n }\n\n return offset;\n }\n\n // puts clones of this.markers into beforeSection and afterSection,\n // all markers before the marker/offset split go in beforeSection, and all\n // after the marker/offset split go in afterSection\n // @return {Array} [beforeSection, afterSection], two new sections\n }, {\n key: '_redistributeMarkers',\n value: function _redistributeMarkers(beforeSection, afterSection, marker) {\n var offset = arguments.length <= 3 || arguments[3] === undefined ? 0 : arguments[3];\n\n var currentSection = beforeSection;\n (0, _mobiledocKitUtilsArrayUtils.forEach)(this.markers, function (m) {\n if (m === marker) {\n var _marker$split = marker.split(offset);\n\n var _marker$split2 = _toArray(_marker$split);\n\n var beforeMarker = _marker$split2[0];\n\n var afterMarkers = _marker$split2.slice(1);\n\n beforeSection.markers.append(beforeMarker);\n (0, _mobiledocKitUtilsArrayUtils.forEach)(afterMarkers, function (_m) {\n return afterSection.markers.append(_m);\n });\n currentSection = afterSection;\n } else {\n currentSection.markers.append(m.clone());\n }\n });\n\n return [beforeSection, afterSection];\n }\n }, {\n key: 'splitAtMarker',\n value: function splitAtMarker() /*marker, offset=0*/{\n (0, _mobiledocKitUtilsAssert['default'])('splitAtMarker must be implemented by sub-class', false);\n }\n\n /**\n * Split this section's marker (if any) at the given offset, so that\n * there is now a marker boundary at that offset (useful for later applying\n * a markup to a range)\n * @param {Number} sectionOffset The offset relative to start of this section\n * @return {EditObject} An edit object with 'removed' and 'added' keys with arrays of Markers. The added markers may be blank.\n * After calling `splitMarkerAtOffset(offset)`, there will always be a valid\n * result returned from `markerBeforeOffset(offset)`.\n */\n }, {\n key: 'splitMarkerAtOffset',\n value: function splitMarkerAtOffset(sectionOffset) {\n (0, _mobiledocKitUtilsAssert['default'])('Cannot splitMarkerAtOffset when offset is > length', sectionOffset <= this.length);\n var markerOffset = undefined;\n var len = 0;\n var currentMarker = this.markers.head;\n var edit = { added: [], removed: [] };\n\n if (!currentMarker) {\n var blankMarker = this.builder.createMarker();\n this.markers.prepend(blankMarker);\n edit.added.push(blankMarker);\n } else {\n while (currentMarker) {\n len += currentMarker.length;\n if (len === sectionOffset) {\n // nothing to do, there is a gap at the requested offset\n break;\n } else if (len > sectionOffset) {\n var _edit$added;\n\n markerOffset = currentMarker.length - (len - sectionOffset);\n var newMarkers = currentMarker.splitAtOffset(markerOffset);\n (_edit$added = edit.added).push.apply(_edit$added, _toConsumableArray(newMarkers));\n edit.removed.push(currentMarker);\n this.markers.splice(currentMarker, 1, newMarkers);\n break;\n } else {\n currentMarker = currentMarker.next;\n }\n }\n }\n\n return edit;\n }\n }, {\n key: 'splitAtPosition',\n value: function splitAtPosition(position) {\n var marker = position.marker;\n var offsetInMarker = position.offsetInMarker;\n\n return this.splitAtMarker(marker, offsetInMarker);\n }\n\n // returns the marker just before this offset.\n // It is an error to call this method with an offset that is in the middle\n // of a marker.\n }, {\n key: 'markerBeforeOffset',\n value: function markerBeforeOffset(sectionOffset) {\n var len = 0;\n var currentMarker = this.markers.head;\n\n while (currentMarker) {\n len += currentMarker.length;\n if (len === sectionOffset) {\n return currentMarker;\n } else {\n (0, _mobiledocKitUtilsAssert['default'])('markerBeforeOffset called with sectionOffset not between markers', len < sectionOffset);\n currentMarker = currentMarker.next;\n }\n }\n }\n }, {\n key: 'markerPositionAtOffset',\n value: function markerPositionAtOffset(offset) {\n var currentOffset = 0;\n var currentMarker = undefined;\n var remaining = offset;\n this.markers.detect(function (marker) {\n currentOffset = Math.min(remaining, marker.length);\n remaining -= currentOffset;\n if (remaining === 0) {\n currentMarker = marker;\n return true; // break out of detect\n }\n });\n\n return { marker: currentMarker, offset: currentOffset };\n }\n }, {\n key: 'markersFor',\n\n /**\n * @return {Array} New markers that match the boundaries of the\n * range. Does not change the existing markers in this section.\n */\n value: function markersFor(headOffset, tailOffset) {\n var range = { head: { section: this, offset: headOffset },\n tail: { section: this, offset: tailOffset } };\n\n var markers = [];\n this._markersInRange(range, function (marker, _ref) {\n var markerHead = _ref.markerHead;\n var markerTail = _ref.markerTail;\n var isContained = _ref.isContained;\n\n var cloned = marker.clone();\n if (!isContained) {\n // cannot do marker.value.slice if the marker is an atom -- this breaks the atom's \"atomic\" value\n // If a marker is an atom `isContained` should always be true so\n // we shouldn't hit this code path. FIXME add tests\n cloned.value = marker.value.slice(markerHead, markerTail);\n }\n markers.push(cloned);\n });\n return markers;\n }\n }, {\n key: 'markupsInRange',\n value: function markupsInRange(range) {\n var markups = new _mobiledocKitUtilsSet['default']();\n this._markersInRange(range, function (marker) {\n marker.markups.forEach(function (m) {\n return markups.add(m);\n });\n });\n return markups.toArray();\n }\n\n // calls the callback with (marker, {markerHead, markerTail, isContained})\n // for each marker that is wholly or partially contained in the range.\n }, {\n key: '_markersInRange',\n value: function _markersInRange(range, callback) {\n var head = range.head;\n var tail = range.tail;\n\n (0, _mobiledocKitUtilsAssert['default'])('Cannot call #_markersInRange if range expands beyond this section', head.section === this && tail.section === this);\n var headOffset = head.offset;var tailOffset = tail.offset;\n\n var currentHead = 0,\n currentTail = 0,\n currentMarker = this.markers.head;\n\n while (currentMarker) {\n currentTail += currentMarker.length;\n\n if (currentTail > headOffset && currentHead < tailOffset) {\n var markerHead = Math.max(headOffset - currentHead, 0);\n var markerTail = currentMarker.length - Math.max(currentTail - tailOffset, 0);\n var isContained = markerHead === 0 && markerTail === currentMarker.length;\n\n callback(currentMarker, { markerHead: markerHead, markerTail: markerTail, isContained: isContained });\n }\n\n currentHead += currentMarker.length;\n currentMarker = currentMarker.next;\n\n if (currentHead > tailOffset) {\n break;\n }\n }\n }\n\n // mutates this by appending the other section's (cloned) markers to it\n }, {\n key: 'join',\n value: function join(otherSection) {\n var _this2 = this;\n\n var beforeMarker = this.markers.tail;\n var afterMarker = null;\n\n otherSection.markers.forEach(function (m) {\n if (!m.isBlank) {\n m = m.clone();\n _this2.markers.append(m);\n if (!afterMarker) {\n afterMarker = m;\n }\n }\n });\n\n return { beforeMarker: beforeMarker, afterMarker: afterMarker };\n }\n }, {\n key: 'isBlank',\n get: function get() {\n if (!this.markers.length) {\n return true;\n }\n return this.markers.every(function (m) {\n return m.isBlank;\n });\n }\n }, {\n key: 'text',\n get: function get() {\n return (0, _mobiledocKitUtilsArrayUtils.reduce)(this.markers, function (prev, m) {\n return prev + m.value;\n }, '');\n }\n }, {\n key: 'length',\n get: function get() {\n return (0, _mobiledocKitUtilsArrayUtils.reduce)(this.markers, function (prev, m) {\n return prev + m.length;\n }, 0);\n }\n }]);\n\n return Markerable;\n })(_mobiledocKitModels_section['default']);\n\n exports['default'] = Markerable;\n});","define('mobiledoc-kit/models/_section', ['exports', 'mobiledoc-kit/utils/dom-utils', 'mobiledoc-kit/utils/linked-item', 'mobiledoc-kit/utils/assert', 'mobiledoc-kit/utils/cursor/position'], function (exports, _mobiledocKitUtilsDomUtils, _mobiledocKitUtilsLinkedItem, _mobiledocKitUtilsAssert, _mobiledocKitUtilsCursorPosition) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n var _get = function get(_x, _x2, _x3) { var _again = true; _function: while (_again) { var object = _x, property = _x2, receiver = _x3; _again = false; if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { _x = parent; _x2 = property; _x3 = receiver; _again = true; desc = parent = undefined; continue _function; } } else if ('value' in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } } };\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n function _inherits(subClass, superClass) { if (typeof superClass !== 'function' && superClass !== null) { throw new TypeError('Super expression must either be null or a function, not ' + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }\n\n function unimplementedMethod(methodName, me) {\n (0, _mobiledocKitUtilsAssert['default'])('`' + methodName + '()` must be implemented by ' + me.constructor.name, false);\n }\n\n var Section = (function (_LinkedItem) {\n _inherits(Section, _LinkedItem);\n\n function Section(type) {\n _classCallCheck(this, Section);\n\n _get(Object.getPrototypeOf(Section.prototype), 'constructor', this).call(this);\n (0, _mobiledocKitUtilsAssert['default'])('Cannot create section without type', !!type);\n this.type = type;\n this.isSection = true;\n this.isMarkerable = false;\n this.isNested = false;\n this.isSection = true;\n this.isLeafSection = true;\n }\n\n _createClass(Section, [{\n key: 'isValidTagName',\n value: function isValidTagName() /* normalizedTagName */{\n unimplementedMethod('isValidTagName', this);\n }\n }, {\n key: 'clone',\n value: function clone() {\n unimplementedMethod('clone', this);\n }\n }, {\n key: 'canJoin',\n value: function canJoin() /* otherSection */{\n unimplementedMethod('canJoin', this);\n }\n\n /**\n * @return {Position} The position at the start of this section\n * @public\n */\n }, {\n key: 'headPosition',\n value: function headPosition() {\n return this.toPosition(0);\n }\n\n /**\n * @return {Position} The position at the end of this section\n * @public\n */\n }, {\n key: 'tailPosition',\n value: function tailPosition() {\n return this.toPosition(this.length);\n }\n\n /**\n * @param {Number} offset\n * @return {Position} The position in this section at the given offset\n * @public\n */\n }, {\n key: 'toPosition',\n value: function toPosition(offset) {\n (0, _mobiledocKitUtilsAssert['default'])(\"Must pass number to `toPosition`\", typeof offset === 'number');\n (0, _mobiledocKitUtilsAssert['default'])(\"Cannot call `toPosition` with offset > length\", offset <= this.length);\n\n return new _mobiledocKitUtilsCursorPosition['default'](this, offset);\n }\n\n /**\n * @return {Range} A range from this section's head to tail positions\n * @public\n */\n }, {\n key: 'toRange',\n value: function toRange() {\n return this.headPosition().toRange(this.tailPosition());\n }\n }, {\n key: 'join',\n value: function join() {\n unimplementedMethod('join', this);\n }\n }, {\n key: 'textUntil',\n value: function textUntil() /* position */{\n return '';\n }\n\n /**\n * Markerable sections should override this method\n */\n }, {\n key: 'splitMarkerAtOffset',\n value: function splitMarkerAtOffset() {\n var blankEdit = { added: [], removed: [] };\n return blankEdit;\n }\n }, {\n key: 'nextLeafSection',\n value: function nextLeafSection() {\n var next = this.next;\n if (next) {\n if (!!next.items) {\n return next.items.head;\n } else {\n return next;\n }\n } else {\n if (this.isNested) {\n return this.parent.nextLeafSection();\n }\n }\n }\n }, {\n key: 'immediatelyNextMarkerableSection',\n value: function immediatelyNextMarkerableSection() {\n var next = this.nextLeafSection();\n while (next && !next.isMarkerable) {\n next = next.nextLeafSection();\n }\n return next;\n }\n }, {\n key: 'previousLeafSection',\n value: function previousLeafSection() {\n var prev = this.prev;\n\n if (prev) {\n if (!!prev.items) {\n return prev.items.tail;\n } else {\n return prev;\n }\n } else {\n if (this.isNested) {\n return this.parent.previousLeafSection();\n }\n }\n }\n }, {\n key: 'tagName',\n set: function set(val) {\n var normalizedTagName = (0, _mobiledocKitUtilsDomUtils.normalizeTagName)(val);\n (0, _mobiledocKitUtilsAssert['default'])('Cannot set section tagName to ' + val, this.isValidTagName(normalizedTagName));\n this._tagName = normalizedTagName;\n },\n get: function get() {\n return this._tagName;\n }\n }, {\n key: 'length',\n get: function get() {\n return 0;\n }\n }, {\n key: 'isBlank',\n get: function get() {\n unimplementedMethod('isBlank', this);\n }\n }]);\n\n return Section;\n })(_mobiledocKitUtilsLinkedItem['default']);\n\n exports['default'] = Section;\n});","define('mobiledoc-kit/models/atom-node', ['exports', 'mobiledoc-kit/utils/assert'], function (exports, _mobiledocKitUtilsAssert) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n var AtomNode = (function () {\n function AtomNode(editor, atom, model, element, atomOptions) {\n _classCallCheck(this, AtomNode);\n\n this.editor = editor;\n this.atom = atom;\n this.model = model;\n this.atomOptions = atomOptions;\n this.element = element;\n\n this._teardownCallback = null;\n this._rendered = null;\n }\n\n _createClass(AtomNode, [{\n key: 'render',\n value: function render() {\n if (!this._rendered) {\n var options = this.atomOptions;\n var env = this.env;\n var _model = this.model;\n var value = _model.value;\n var payload = _model.payload;\n\n // cache initial render\n this._rendered = this.atom.render({ options: options, env: env, value: value, payload: payload });\n }\n\n this._validateAndAppendRenderResult(this._rendered);\n }\n }, {\n key: 'teardown',\n value: function teardown() {\n if (this._teardownCallback) {\n this._teardownCallback();\n this._teardownCallback = null;\n }\n if (this._rendered) {\n this.element.removeChild(this._rendered);\n this._rendered = null;\n }\n }\n }, {\n key: '_validateAndAppendRenderResult',\n value: function _validateAndAppendRenderResult(rendered) {\n if (!rendered) {\n return;\n }\n\n var name = this.atom.name;\n\n (0, _mobiledocKitUtilsAssert['default'])('Atom \"' + name + '\" must return a DOM node (returned value was: \"' + rendered + '\")', !!rendered.nodeType);\n this.element.appendChild(rendered);\n }\n }, {\n key: 'env',\n get: function get() {\n var _this = this;\n\n return {\n name: this.atom.name,\n onTeardown: function onTeardown(callback) {\n return _this._teardownCallback = callback;\n },\n save: function save(value) {\n var payload = arguments.length <= 1 || arguments[1] === undefined ? {} : arguments[1];\n\n _this.model.value = value;\n _this.model.payload = payload;\n\n _this.editor._postDidChange();\n _this.teardown();\n _this.render();\n }\n };\n }\n }]);\n\n return AtomNode;\n })();\n\n exports['default'] = AtomNode;\n});","define('mobiledoc-kit/models/atom', ['exports', 'mobiledoc-kit/models/types', 'mobiledoc-kit/utils/mixin', 'mobiledoc-kit/utils/markuperable', 'mobiledoc-kit/utils/linked-item', 'mobiledoc-kit/utils/assert'], function (exports, _mobiledocKitModelsTypes, _mobiledocKitUtilsMixin, _mobiledocKitUtilsMarkuperable, _mobiledocKitUtilsLinkedItem, _mobiledocKitUtilsAssert) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n var _get = function get(_x4, _x5, _x6) { var _again = true; _function: while (_again) { var object = _x4, property = _x5, receiver = _x6; _again = false; if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { _x4 = parent; _x5 = property; _x6 = receiver; _again = true; desc = parent = undefined; continue _function; } } else if ('value' in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } } };\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n function _inherits(subClass, superClass) { if (typeof superClass !== 'function' && superClass !== null) { throw new TypeError('Super expression must either be null or a function, not ' + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }\n\n var ATOM_LENGTH = 1;\n\n var Atom = (function (_LinkedItem) {\n _inherits(Atom, _LinkedItem);\n\n function Atom(name, value, payload) {\n var _this = this;\n\n var markups = arguments.length <= 3 || arguments[3] === undefined ? [] : arguments[3];\n\n _classCallCheck(this, Atom);\n\n _get(Object.getPrototypeOf(Atom.prototype), 'constructor', this).call(this);\n this.name = name;\n this.value = value;\n this.text = ''; // An atom never has text, but it does have a value\n (0, _mobiledocKitUtilsAssert['default'])('Atom must have value', value !== undefined && value !== null);\n this.payload = payload;\n this.type = _mobiledocKitModelsTypes.ATOM_TYPE;\n this.isMarker = false;\n this.isAtom = true;\n\n this.markups = [];\n markups.forEach(function (m) {\n return _this.addMarkup(m);\n });\n }\n\n _createClass(Atom, [{\n key: 'clone',\n value: function clone() {\n var clonedMarkups = this.markups.slice();\n return this.builder.createAtom(this.name, this.value, this.payload, clonedMarkups);\n }\n }, {\n key: 'canJoin',\n value: function canJoin() /* other */{\n return false;\n }\n }, {\n key: 'textUntil',\n value: function textUntil() /* offset */{\n return '';\n }\n }, {\n key: 'split',\n value: function split() {\n var offset = arguments.length <= 0 || arguments[0] === undefined ? 0 : arguments[0];\n var endOffset = arguments.length <= 1 || arguments[1] === undefined ? offset : arguments[1];\n return (function () {\n var markers = [];\n\n if (endOffset === 0) {\n markers.push(this.builder.createMarker('', this.markups.slice()));\n }\n\n markers.push(this.clone());\n\n if (offset === ATOM_LENGTH) {\n markers.push(this.builder.createMarker('', this.markups.slice()));\n }\n\n return markers;\n }).apply(this, arguments);\n }\n }, {\n key: 'splitAtOffset',\n value: function splitAtOffset(offset) {\n (0, _mobiledocKitUtilsAssert['default'])('Cannot split a marker at an offset > its length', offset <= this.length);\n\n var builder = this.builder;\n\n var clone = this.clone();\n var blankMarker = builder.createMarker('');\n var pre = undefined,\n post = undefined;\n\n if (offset === 0) {\n pre = blankMarker;\n post = clone;\n } else if (offset === ATOM_LENGTH) {\n pre = clone;\n post = blankMarker;\n } else {\n (0, _mobiledocKitUtilsAssert['default'])('Invalid offset given to Atom#splitAtOffset: \"' + offset + '\"', false);\n }\n\n this.markups.forEach(function (markup) {\n pre.addMarkup(markup);\n post.addMarkup(markup);\n });\n return [pre, post];\n }\n }, {\n key: 'isBlank',\n get: function get() {\n return false;\n }\n }, {\n key: 'length',\n get: function get() {\n return ATOM_LENGTH;\n }\n }]);\n\n return Atom;\n })(_mobiledocKitUtilsLinkedItem['default']);\n\n (0, _mobiledocKitUtilsMixin['default'])(Atom, _mobiledocKitUtilsMarkuperable['default']);\n\n exports['default'] = Atom;\n});","define('mobiledoc-kit/models/card-node', ['exports', 'mobiledoc-kit/utils/assert'], function (exports, _mobiledocKitUtilsAssert) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n var CardNode = (function () {\n function CardNode(editor, card, section, element, options) {\n _classCallCheck(this, CardNode);\n\n this.editor = editor;\n this.card = card;\n this.section = section;\n this.element = element;\n this.options = options;\n\n this.mode = null;\n\n this._teardownCallback = null;\n this._rendered = null;\n }\n\n _createClass(CardNode, [{\n key: 'render',\n value: function render(mode) {\n if (this.mode === mode) {\n return;\n }\n\n this.teardown();\n\n this.mode = mode;\n\n var method = mode === 'display' ? 'render' : 'edit';\n method = this.card[method];\n\n (0, _mobiledocKitUtilsAssert['default'])('Card is missing \"' + method + '\" (tried to render mode: \"' + mode + '\")', !!method);\n var rendered = method({\n env: this.env,\n options: this.options,\n payload: this.section.payload\n });\n\n this._validateAndAppendRenderResult(rendered);\n }\n }, {\n key: 'teardown',\n value: function teardown() {\n if (this._teardownCallback) {\n this._teardownCallback();\n this._teardownCallback = null;\n }\n if (this._rendered) {\n this.element.removeChild(this._rendered);\n this._rendered = null;\n }\n }\n }, {\n key: 'didRender',\n value: function didRender() {\n if (this._didRenderCallback) {\n this._didRenderCallback();\n }\n }\n }, {\n key: 'display',\n value: function display() {\n this.render('display');\n }\n }, {\n key: 'edit',\n value: function edit() {\n this.render('edit');\n }\n }, {\n key: 'remove',\n value: function remove() {\n var _this = this;\n\n this.editor.run(function (postEditor) {\n return postEditor.removeSection(_this.section);\n });\n }\n }, {\n key: '_validateAndAppendRenderResult',\n value: function _validateAndAppendRenderResult(rendered) {\n if (!rendered) {\n return;\n }\n\n var name = this.card.name;\n\n (0, _mobiledocKitUtilsAssert['default'])('Card \"' + name + '\" must render dom (render value was: \"' + rendered + '\")', !!rendered.nodeType);\n this.element.appendChild(rendered);\n this._rendered = rendered;\n this.didRender();\n }\n }, {\n key: 'env',\n get: function get() {\n var _this2 = this;\n\n return {\n name: this.card.name,\n isInEditor: true,\n onTeardown: function onTeardown(callback) {\n return _this2._teardownCallback = callback;\n },\n didRender: function didRender(callback) {\n return _this2._didRenderCallback = callback;\n },\n edit: function edit() {\n return _this2.edit();\n },\n save: function save(payload) {\n var transition = arguments.length <= 1 || arguments[1] === undefined ? true : arguments[1];\n\n _this2.section.payload = payload;\n\n _this2.editor._postDidChange();\n if (transition) {\n _this2.display();\n }\n },\n cancel: function cancel() {\n return _this2.display();\n },\n remove: function remove() {\n return _this2.remove();\n },\n postModel: this.section\n };\n }\n }]);\n\n return CardNode;\n })();\n\n exports['default'] = CardNode;\n});","define('mobiledoc-kit/models/card', ['exports', 'mobiledoc-kit/models/_section', 'mobiledoc-kit/models/types', 'mobiledoc-kit/utils/copy'], function (exports, _mobiledocKitModels_section, _mobiledocKitModelsTypes, _mobiledocKitUtilsCopy) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n var _get = function get(_x, _x2, _x3) { var _again = true; _function: while (_again) { var object = _x, property = _x2, receiver = _x3; _again = false; if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { _x = parent; _x2 = property; _x3 = receiver; _again = true; desc = parent = undefined; continue _function; } } else if ('value' in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } } };\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n function _inherits(subClass, superClass) { if (typeof superClass !== 'function' && superClass !== null) { throw new TypeError('Super expression must either be null or a function, not ' + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }\n\n var CARD_MODES = {\n DISPLAY: 'display',\n EDIT: 'edit'\n };\n\n exports.CARD_MODES = CARD_MODES;\n var CARD_LENGTH = 1;\n\n var DEFAULT_INITIAL_MODE = CARD_MODES.DISPLAY;\n\n var Card = (function (_Section) {\n _inherits(Card, _Section);\n\n function Card(name, payload) {\n _classCallCheck(this, Card);\n\n _get(Object.getPrototypeOf(Card.prototype), 'constructor', this).call(this, _mobiledocKitModelsTypes.CARD_TYPE);\n this.name = name;\n this.payload = payload;\n this.setInitialMode(DEFAULT_INITIAL_MODE);\n this.isCardSection = true;\n }\n\n _createClass(Card, [{\n key: 'canJoin',\n value: function canJoin() {\n return false;\n }\n }, {\n key: 'clone',\n value: function clone() {\n var payload = (0, _mobiledocKitUtilsCopy.shallowCopyObject)(this.payload);\n var card = this.builder.createCardSection(this.name, payload);\n // If this card is currently rendered, clone the mode it is\n // currently in as the default mode of the new card.\n var mode = this._initialMode;\n if (this.renderNode && this.renderNode.cardNode) {\n mode = this.renderNode.cardNode.mode;\n }\n card.setInitialMode(mode);\n return card;\n }\n\n /**\n * set the mode that this will be rendered into initially\n * @private\n */\n }, {\n key: 'setInitialMode',\n value: function setInitialMode(initialMode) {\n // TODO validate initialMode\n this._initialMode = initialMode;\n }\n }, {\n key: 'isBlank',\n get: function get() {\n return false;\n }\n }, {\n key: 'length',\n get: function get() {\n return CARD_LENGTH;\n }\n }]);\n\n return Card;\n })(_mobiledocKitModels_section['default']);\n\n exports['default'] = Card;\n});","define('mobiledoc-kit/models/image', ['exports', 'mobiledoc-kit/models/types', 'mobiledoc-kit/models/_section'], function (exports, _mobiledocKitModelsTypes, _mobiledocKitModels_section) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n var _get = function get(_x, _x2, _x3) { var _again = true; _function: while (_again) { var object = _x, property = _x2, receiver = _x3; _again = false; if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { _x = parent; _x2 = property; _x3 = receiver; _again = true; desc = parent = undefined; continue _function; } } else if ('value' in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } } };\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n function _inherits(subClass, superClass) { if (typeof superClass !== 'function' && superClass !== null) { throw new TypeError('Super expression must either be null or a function, not ' + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }\n\n var Image = (function (_Section) {\n _inherits(Image, _Section);\n\n function Image() {\n _classCallCheck(this, Image);\n\n _get(Object.getPrototypeOf(Image.prototype), 'constructor', this).call(this, _mobiledocKitModelsTypes.IMAGE_SECTION_TYPE);\n this.src = null;\n }\n\n _createClass(Image, [{\n key: 'canJoin',\n value: function canJoin() {\n return false;\n }\n }, {\n key: 'isBlank',\n get: function get() {\n return false;\n }\n }, {\n key: 'length',\n get: function get() {\n return 1;\n }\n }]);\n\n return Image;\n })(_mobiledocKitModels_section['default']);\n\n exports['default'] = Image;\n});","define('mobiledoc-kit/models/lifecycle-callbacks', ['exports', 'mobiledoc-kit/utils/assert'], function (exports, _mobiledocKitUtilsAssert) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _toConsumableArray(arr) { if (Array.isArray(arr)) { for (var i = 0, arr2 = Array(arr.length); i < arr.length; i++) arr2[i] = arr[i]; return arr2; } else { return Array.from(arr); } }\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n var LifecycleCallbacks = (function () {\n function LifecycleCallbacks() {\n var _this = this;\n\n var queueNames = arguments.length <= 0 || arguments[0] === undefined ? [] : arguments[0];\n\n _classCallCheck(this, LifecycleCallbacks);\n\n this.callbackQueues = {};\n this.removalQueues = {};\n\n queueNames.forEach(function (name) {\n _this.callbackQueues[name] = [];\n _this.removalQueues[name] = [];\n });\n }\n\n _createClass(LifecycleCallbacks, [{\n key: 'runCallbacks',\n value: function runCallbacks(queueName) {\n var args = arguments.length <= 1 || arguments[1] === undefined ? [] : arguments[1];\n\n var queue = this._getQueue(queueName);\n queue.forEach(function (cb) {\n return cb.apply(undefined, _toConsumableArray(args));\n });\n\n var toRemove = this.removalQueues[queueName];\n toRemove.forEach(function (cb) {\n var index = queue.indexOf(cb);\n if (index !== -1) {\n queue.splice(index, 1);\n }\n });\n\n this.removalQueues[queueName] = [];\n }\n }, {\n key: 'addCallback',\n value: function addCallback(queueName, callback) {\n this._getQueue(queueName).push(callback);\n }\n }, {\n key: '_scheduleCallbackForRemoval',\n value: function _scheduleCallbackForRemoval(queueName, callback) {\n this.removalQueues[queueName].push(callback);\n }\n }, {\n key: 'addCallbackOnce',\n value: function addCallbackOnce(queueName, callback) {\n var queue = this._getQueue(queueName);\n if (queue.indexOf(callback) === -1) {\n queue.push(callback);\n this._scheduleCallbackForRemoval(queueName, callback);\n }\n }\n }, {\n key: '_getQueue',\n value: function _getQueue(queueName) {\n var queue = this.callbackQueues[queueName];\n (0, _mobiledocKitUtilsAssert['default'])('No queue found for \"' + queueName + '\"', !!queue);\n return queue;\n }\n }]);\n\n return LifecycleCallbacks;\n })();\n\n exports['default'] = LifecycleCallbacks;\n});","define('mobiledoc-kit/models/list-item', ['exports', 'mobiledoc-kit/models/_markerable', 'mobiledoc-kit/models/types', 'mobiledoc-kit/utils/dom-utils', 'mobiledoc-kit/utils/array-utils'], function (exports, _mobiledocKitModels_markerable, _mobiledocKitModelsTypes, _mobiledocKitUtilsDomUtils, _mobiledocKitUtilsArrayUtils) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n var _get = function get(_x3, _x4, _x5) { var _again = true; _function: while (_again) { var object = _x3, property = _x4, receiver = _x5; _again = false; if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { _x3 = parent; _x4 = property; _x5 = receiver; _again = true; desc = parent = undefined; continue _function; } } else if ('value' in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } } };\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n function _inherits(subClass, superClass) { if (typeof superClass !== 'function' && superClass !== null) { throw new TypeError('Super expression must either be null or a function, not ' + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }\n\n var VALID_LIST_ITEM_TAGNAMES = ['li'].map(_mobiledocKitUtilsDomUtils.normalizeTagName);\n\n exports.VALID_LIST_ITEM_TAGNAMES = VALID_LIST_ITEM_TAGNAMES;\n\n var ListItem = (function (_Markerable) {\n _inherits(ListItem, _Markerable);\n\n function ListItem(tagName) {\n var markers = arguments.length <= 1 || arguments[1] === undefined ? [] : arguments[1];\n\n _classCallCheck(this, ListItem);\n\n _get(Object.getPrototypeOf(ListItem.prototype), 'constructor', this).call(this, _mobiledocKitModelsTypes.LIST_ITEM_TYPE, tagName, markers);\n this.isListItem = true;\n this.isNested = true;\n }\n\n _createClass(ListItem, [{\n key: 'isValidTagName',\n value: function isValidTagName(normalizedTagName) {\n return (0, _mobiledocKitUtilsArrayUtils.contains)(VALID_LIST_ITEM_TAGNAMES, normalizedTagName);\n }\n }, {\n key: 'splitAtMarker',\n value: function splitAtMarker(marker) {\n var offset = arguments.length <= 1 || arguments[1] === undefined ? 0 : arguments[1];\n\n // FIXME need to check if we are going to split into two list items\n // or a list item and a new markup section:\n var isLastItem = !this.next;\n var createNewSection = !marker && offset === 0 && isLastItem;\n\n var beforeSection = this.builder.createListItem();\n var afterSection = createNewSection ? this.builder.createMarkupSection() : this.builder.createListItem();\n\n return this._redistributeMarkers(beforeSection, afterSection, marker, offset);\n }\n }, {\n key: 'post',\n get: function get() {\n return this.section.post;\n }\n }]);\n\n return ListItem;\n })(_mobiledocKitModels_markerable['default']);\n\n exports['default'] = ListItem;\n});","define('mobiledoc-kit/models/list-section', ['exports', 'mobiledoc-kit/utils/linked-list', 'mobiledoc-kit/utils/array-utils', 'mobiledoc-kit/models/types', 'mobiledoc-kit/models/_section', 'mobiledoc-kit/utils/dom-utils', 'mobiledoc-kit/utils/assert'], function (exports, _mobiledocKitUtilsLinkedList, _mobiledocKitUtilsArrayUtils, _mobiledocKitModelsTypes, _mobiledocKitModels_section, _mobiledocKitUtilsDomUtils, _mobiledocKitUtilsAssert) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n var _get = function get(_x3, _x4, _x5) { var _again = true; _function: while (_again) { var object = _x3, property = _x4, receiver = _x5; _again = false; if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { _x3 = parent; _x4 = property; _x5 = receiver; _again = true; desc = parent = undefined; continue _function; } } else if ('value' in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } } };\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n function _inherits(subClass, superClass) { if (typeof superClass !== 'function' && superClass !== null) { throw new TypeError('Super expression must either be null or a function, not ' + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }\n\n var VALID_LIST_SECTION_TAGNAMES = ['ul', 'ol'].map(_mobiledocKitUtilsDomUtils.normalizeTagName);\n\n exports.VALID_LIST_SECTION_TAGNAMES = VALID_LIST_SECTION_TAGNAMES;\n var DEFAULT_TAG_NAME = VALID_LIST_SECTION_TAGNAMES[0];\n\n exports.DEFAULT_TAG_NAME = DEFAULT_TAG_NAME;\n\n var ListSection = (function (_Section) {\n _inherits(ListSection, _Section);\n\n function ListSection() {\n var _this = this;\n\n var tagName = arguments.length <= 0 || arguments[0] === undefined ? DEFAULT_TAG_NAME : arguments[0];\n var items = arguments.length <= 1 || arguments[1] === undefined ? [] : arguments[1];\n\n _classCallCheck(this, ListSection);\n\n _get(Object.getPrototypeOf(ListSection.prototype), 'constructor', this).call(this, _mobiledocKitModelsTypes.LIST_SECTION_TYPE);\n this.tagName = tagName;\n this.isListSection = true;\n this.isLeafSection = false;\n\n this.items = new _mobiledocKitUtilsLinkedList['default']({\n adoptItem: function adoptItem(i) {\n (0, _mobiledocKitUtilsAssert['default'])('Cannot insert non-list-item to list (is: ' + i.type + ')', i.isListItem);\n i.section = i.parent = _this;\n },\n freeItem: function freeItem(i) {\n return i.section = i.parent = null;\n }\n });\n this.sections = this.items;\n\n items.forEach(function (i) {\n return _this.items.append(i);\n });\n }\n\n _createClass(ListSection, [{\n key: 'canJoin',\n value: function canJoin() {\n return false;\n }\n }, {\n key: 'isValidTagName',\n value: function isValidTagName(normalizedTagName) {\n return (0, _mobiledocKitUtilsArrayUtils.contains)(VALID_LIST_SECTION_TAGNAMES, normalizedTagName);\n }\n }, {\n key: 'headPosition',\n value: function headPosition() {\n return this.items.head.headPosition();\n }\n }, {\n key: 'tailPosition',\n value: function tailPosition() {\n return this.items.tail.tailPosition();\n }\n }, {\n key: 'clone',\n value: function clone() {\n var newSection = this.builder.createListSection(this.tagName);\n (0, _mobiledocKitUtilsArrayUtils.forEach)(this.items, function (i) {\n return newSection.items.append(i.clone());\n });\n return newSection;\n }\n\n /**\n * Mutates this list\n * @param {ListSection|Markerable}\n * @return null\n */\n }, {\n key: 'join',\n value: function join(other) {\n var _this2 = this;\n\n if (other.isListSection) {\n other.items.forEach(function (i) {\n return _this2.join(i);\n });\n } else if (other.isMarkerable) {\n var item = this.builder.createListItem();\n item.join(other);\n this.items.append(item);\n }\n }\n }, {\n key: 'isBlank',\n get: function get() {\n return this.items.isEmpty;\n }\n }]);\n\n return ListSection;\n })(_mobiledocKitModels_section['default']);\n\n exports['default'] = ListSection;\n});","define('mobiledoc-kit/models/marker', ['exports', 'mobiledoc-kit/models/types', 'mobiledoc-kit/utils/mixin', 'mobiledoc-kit/utils/markuperable', 'mobiledoc-kit/utils/linked-item', 'mobiledoc-kit/utils/assert', 'mobiledoc-kit/utils/array-utils'], function (exports, _mobiledocKitModelsTypes, _mobiledocKitUtilsMixin, _mobiledocKitUtilsMarkuperable, _mobiledocKitUtilsLinkedItem, _mobiledocKitUtilsAssert, _mobiledocKitUtilsArrayUtils) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n var _get = function get(_x5, _x6, _x7) { var _again = true; _function: while (_again) { var object = _x5, property = _x6, receiver = _x7; _again = false; if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { _x5 = parent; _x6 = property; _x7 = receiver; _again = true; desc = parent = undefined; continue _function; } } else if ('value' in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } } };\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n function _inherits(subClass, superClass) { if (typeof superClass !== 'function' && superClass !== null) { throw new TypeError('Super expression must either be null or a function, not ' + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }\n\n // Unicode uses a pair of \"surrogate\" characters\" (a high- and low-surrogate)\n // to encode characters outside the basic multilingual plane (like emoji and\n // some languages).\n // These values are the unicode code points for the start and end of the\n // high- and low-surrogate characters.\n // See \"high surrogate\" and \"low surrogate\" on\n // https://en.wikipedia.org/wiki/Unicode_block\n var HIGH_SURROGATE_RANGE = [0xD800, 0xDBFF];\n exports.HIGH_SURROGATE_RANGE = HIGH_SURROGATE_RANGE;\n var LOW_SURROGATE_RANGE = [0xDC00, 0xDFFF];\n\n exports.LOW_SURROGATE_RANGE = LOW_SURROGATE_RANGE;\n var Marker = (function (_LinkedItem) {\n _inherits(Marker, _LinkedItem);\n\n function Marker() {\n var _this = this;\n\n var value = arguments.length <= 0 || arguments[0] === undefined ? '' : arguments[0];\n var markups = arguments.length <= 1 || arguments[1] === undefined ? [] : arguments[1];\n\n _classCallCheck(this, Marker);\n\n _get(Object.getPrototypeOf(Marker.prototype), 'constructor', this).call(this);\n this.value = value;\n (0, _mobiledocKitUtilsAssert['default'])('Marker must have value', value !== undefined && value !== null);\n this.markups = [];\n this.type = _mobiledocKitModelsTypes.MARKER_TYPE;\n this.isMarker = true;\n this.isAtom = false;\n markups.forEach(function (m) {\n return _this.addMarkup(m);\n });\n }\n\n _createClass(Marker, [{\n key: 'clone',\n value: function clone() {\n var clonedMarkups = this.markups.slice();\n return this.builder.createMarker(this.value, clonedMarkups);\n }\n }, {\n key: 'charAt',\n value: function charAt(offset) {\n return this.value.slice(offset, offset + 1);\n }\n\n /**\n * A marker's text is equal to its value.\n * Compare with an Atom which distinguishes between text and value\n */\n }, {\n key: 'deleteValueAtOffset',\n\n // delete the character at this offset,\n // update the value with the new value\n value: function deleteValueAtOffset(offset) {\n (0, _mobiledocKitUtilsAssert['default'])('Cannot delete value at offset outside bounds', offset >= 0 && offset <= this.length);\n\n var width = 1;\n var code = this.value.charCodeAt(offset);\n if (code >= HIGH_SURROGATE_RANGE[0] && code <= HIGH_SURROGATE_RANGE[1]) {\n width = 2;\n } else if (code >= LOW_SURROGATE_RANGE[0] && code <= LOW_SURROGATE_RANGE[1]) {\n width = 2;\n offset = offset - 1;\n }\n\n var left = this.value.slice(0, offset);\n var right = this.value.slice(offset + width);\n\n this.value = left + right;\n\n return width;\n }\n }, {\n key: 'canJoin',\n value: function canJoin(other) {\n return other && other.isMarker && (0, _mobiledocKitUtilsArrayUtils.isArrayEqual)(this.markups, other.markups);\n }\n }, {\n key: 'textUntil',\n value: function textUntil(offset) {\n return this.value.slice(0, offset);\n }\n }, {\n key: 'split',\n value: function split() {\n var offset = arguments.length <= 0 || arguments[0] === undefined ? 0 : arguments[0];\n var endOffset = arguments.length <= 1 || arguments[1] === undefined ? this.length : arguments[1];\n\n var markers = [this.builder.createMarker(this.value.substring(0, offset)), this.builder.createMarker(this.value.substring(offset, endOffset)), this.builder.createMarker(this.value.substring(endOffset))];\n\n this.markups.forEach(function (mu) {\n return markers.forEach(function (m) {\n return m.addMarkup(mu);\n });\n });\n return markers;\n }\n\n /**\n * @return {Array} 2 markers either or both of which could be blank\n */\n }, {\n key: 'splitAtOffset',\n value: function splitAtOffset(offset) {\n (0, _mobiledocKitUtilsAssert['default'])('Cannot split a marker at an offset > its length', offset <= this.length);\n var value = this.value;\n var builder = this.builder;\n\n var pre = builder.createMarker(value.substring(0, offset));\n var post = builder.createMarker(value.substring(offset));\n\n this.markups.forEach(function (markup) {\n pre.addMarkup(markup);\n post.addMarkup(markup);\n });\n\n return [pre, post];\n }\n }, {\n key: 'isEmpty',\n get: function get() {\n return this.isBlank;\n }\n }, {\n key: 'isBlank',\n get: function get() {\n return this.length === 0;\n }\n }, {\n key: 'text',\n get: function get() {\n return this.value;\n }\n }, {\n key: 'length',\n get: function get() {\n return this.value.length;\n }\n }]);\n\n return Marker;\n })(_mobiledocKitUtilsLinkedItem['default']);\n\n (0, _mobiledocKitUtilsMixin['default'])(Marker, _mobiledocKitUtilsMarkuperable['default']);\n\n exports['default'] = Marker;\n});","define('mobiledoc-kit/models/markup-section', ['exports', 'mobiledoc-kit/models/_markerable', 'mobiledoc-kit/utils/dom-utils', 'mobiledoc-kit/utils/array-utils', 'mobiledoc-kit/models/types'], function (exports, _mobiledocKitModels_markerable, _mobiledocKitUtilsDomUtils, _mobiledocKitUtilsArrayUtils, _mobiledocKitModelsTypes) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n var _get = function get(_x4, _x5, _x6) { var _again = true; _function: while (_again) { var object = _x4, property = _x5, receiver = _x6; _again = false; if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { _x4 = parent; _x5 = property; _x6 = receiver; _again = true; desc = parent = undefined; continue _function; } } else if ('value' in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } } };\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n function _inherits(subClass, superClass) { if (typeof superClass !== 'function' && superClass !== null) { throw new TypeError('Super expression must either be null or a function, not ' + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }\n\n // valid values of `tagName` for a MarkupSection\n var VALID_MARKUP_SECTION_TAGNAMES = ['aside', 'blockquote', 'h1', 'h2', 'h3', 'h4', 'h5', 'h6', 'p'].map(_mobiledocKitUtilsDomUtils.normalizeTagName);\n\n exports.VALID_MARKUP_SECTION_TAGNAMES = VALID_MARKUP_SECTION_TAGNAMES;\n // valid element names for a MarkupSection. A MarkupSection with a tagName\n // not in this will be rendered as a div with a className matching the\n // tagName\n var MARKUP_SECTION_ELEMENT_NAMES = ['aside', 'blockquote', 'h1', 'h2', 'h3', 'h4', 'h5', 'h6', 'p'].map(_mobiledocKitUtilsDomUtils.normalizeTagName);\n exports.MARKUP_SECTION_ELEMENT_NAMES = MARKUP_SECTION_ELEMENT_NAMES;\n var DEFAULT_TAG_NAME = VALID_MARKUP_SECTION_TAGNAMES[8];\n\n exports.DEFAULT_TAG_NAME = DEFAULT_TAG_NAME;\n var MarkupSection = (function (_Markerable) {\n _inherits(MarkupSection, _Markerable);\n\n function MarkupSection() {\n var tagName = arguments.length <= 0 || arguments[0] === undefined ? DEFAULT_TAG_NAME : arguments[0];\n var markers = arguments.length <= 1 || arguments[1] === undefined ? [] : arguments[1];\n\n _classCallCheck(this, MarkupSection);\n\n _get(Object.getPrototypeOf(MarkupSection.prototype), 'constructor', this).call(this, _mobiledocKitModelsTypes.MARKUP_SECTION_TYPE, tagName, markers);\n this.isMarkupSection = true;\n }\n\n _createClass(MarkupSection, [{\n key: 'isValidTagName',\n value: function isValidTagName(normalizedTagName) {\n return (0, _mobiledocKitUtilsArrayUtils.contains)(VALID_MARKUP_SECTION_TAGNAMES, normalizedTagName);\n }\n }, {\n key: 'splitAtMarker',\n value: function splitAtMarker(marker) {\n var offset = arguments.length <= 1 || arguments[1] === undefined ? 0 : arguments[1];\n var beforeSection = this.builder.createMarkupSection(this.tagName, []);\n var afterSection = this.builder.createMarkupSection();\n\n return this._redistributeMarkers(beforeSection, afterSection, marker, offset);\n }\n }]);\n\n return MarkupSection;\n })(_mobiledocKitModels_markerable['default']);\n\n exports['default'] = MarkupSection;\n});","define('mobiledoc-kit/models/markup', ['exports', 'mobiledoc-kit/utils/dom-utils', 'mobiledoc-kit/utils/array-utils', 'mobiledoc-kit/models/types', 'mobiledoc-kit/utils/assert'], function (exports, _mobiledocKitUtilsDomUtils, _mobiledocKitUtilsArrayUtils, _mobiledocKitModelsTypes, _mobiledocKitUtilsAssert) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n var VALID_MARKUP_TAGNAMES = ['a', 'b', 'code', 'em', 'i', 's', // strikethrough\n 'strong', 'sub', // subscript\n 'sup', // superscript\n 'u'].map(_mobiledocKitUtilsDomUtils.normalizeTagName);\n\n exports.VALID_MARKUP_TAGNAMES = VALID_MARKUP_TAGNAMES;\n var VALID_ATTRIBUTES = ['href', 'rel'];\n\n exports.VALID_ATTRIBUTES = VALID_ATTRIBUTES;\n\n var Markup = (function () {\n /*\n * @param {Object} attributes key-values\n */\n\n function Markup(tagName) {\n var attributes = arguments.length <= 1 || arguments[1] === undefined ? {} : arguments[1];\n\n _classCallCheck(this, Markup);\n\n this.tagName = (0, _mobiledocKitUtilsDomUtils.normalizeTagName)(tagName);\n\n (0, _mobiledocKitUtilsAssert['default'])('Must use attributes object param (not array) for Markup', !Array.isArray(attributes));\n\n this.attributes = (0, _mobiledocKitUtilsArrayUtils.filterObject)(attributes, VALID_ATTRIBUTES);\n this.type = _mobiledocKitModelsTypes.MARKUP_TYPE;\n\n (0, _mobiledocKitUtilsAssert['default'])('Cannot create markup of tagName ' + tagName, VALID_MARKUP_TAGNAMES.indexOf(this.tagName) !== -1);\n }\n\n _createClass(Markup, [{\n key: 'isForwardInclusive',\n value: function isForwardInclusive() {\n return this.tagName === (0, _mobiledocKitUtilsDomUtils.normalizeTagName)(\"a\") ? false : true;\n }\n }, {\n key: 'isBackwardInclusive',\n value: function isBackwardInclusive() {\n return false;\n }\n }, {\n key: 'hasTag',\n value: function hasTag(tagName) {\n return this.tagName === (0, _mobiledocKitUtilsDomUtils.normalizeTagName)(tagName);\n }\n }, {\n key: 'getAttribute',\n value: function getAttribute(name) {\n return this.attributes[name];\n }\n }], [{\n key: 'isValidElement',\n value: function isValidElement(element) {\n var tagName = (0, _mobiledocKitUtilsDomUtils.normalizeTagName)(element.tagName);\n return VALID_MARKUP_TAGNAMES.indexOf(tagName) !== -1;\n }\n }]);\n\n return Markup;\n })();\n\n exports['default'] = Markup;\n});","define('mobiledoc-kit/models/post-node-builder', ['exports', 'mobiledoc-kit/models/atom', 'mobiledoc-kit/models/post', 'mobiledoc-kit/models/markup-section', 'mobiledoc-kit/models/list-section', 'mobiledoc-kit/models/list-item', 'mobiledoc-kit/models/image', 'mobiledoc-kit/models/marker', 'mobiledoc-kit/models/markup', 'mobiledoc-kit/models/card', 'mobiledoc-kit/utils/dom-utils', 'mobiledoc-kit/utils/array-utils', 'mobiledoc-kit/models/types', 'mobiledoc-kit/utils/assert'], function (exports, _mobiledocKitModelsAtom, _mobiledocKitModelsPost, _mobiledocKitModelsMarkupSection, _mobiledocKitModelsListSection, _mobiledocKitModelsListItem, _mobiledocKitModelsImage, _mobiledocKitModelsMarker, _mobiledocKitModelsMarkup, _mobiledocKitModelsCard, _mobiledocKitUtilsDomUtils, _mobiledocKitUtilsArrayUtils, _mobiledocKitModelsTypes, _mobiledocKitUtilsAssert) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n function cacheKey(tagName, attributes) {\n return (0, _mobiledocKitUtilsDomUtils.normalizeTagName)(tagName) + '-' + (0, _mobiledocKitUtilsArrayUtils.objectToSortedKVArray)(attributes).join('-');\n }\n\n function addMarkupToCache(cache, markup) {\n cache[cacheKey(markup.tagName, markup.attributes)] = markup;\n }\n\n function findMarkupInCache(cache, tagName, attributes) {\n var key = cacheKey(tagName, attributes);\n return cache[key];\n }\n\n /**\n * The PostNodeBuilder is used to create new {@link Post} primitives, such\n * as a MarkupSection, a CardSection, a Markup, etc. Every instance of an\n * {@link Editor} has its own builder instance. The builder can be used\n * inside an {@link Editor#run} callback to programmatically create new\n * Post primitives to insert into the document.\n * A PostNodeBuilder should be read from the Editor, *not* instantiated on its own.\n */\n\n var PostNodeBuilder = (function () {\n /**\n * @private\n */\n\n function PostNodeBuilder() {\n _classCallCheck(this, PostNodeBuilder);\n\n this.markupCache = {};\n }\n\n /**\n * @return {Post} A new, blank post\n */\n\n _createClass(PostNodeBuilder, [{\n key: 'createPost',\n value: function createPost() {\n var sections = arguments.length <= 0 || arguments[0] === undefined ? [] : arguments[0];\n\n var post = new _mobiledocKitModelsPost['default']();\n post.builder = this;\n\n sections.forEach(function (s) {\n return post.sections.append(s);\n });\n\n return post;\n }\n }, {\n key: 'createMarkerableSection',\n value: function createMarkerableSection(type, tagName) {\n var markers = arguments.length <= 2 || arguments[2] === undefined ? [] : arguments[2];\n\n switch (type) {\n case _mobiledocKitModelsTypes.LIST_ITEM_TYPE:\n return this.createListItem(markers);\n case _mobiledocKitModelsTypes.MARKUP_SECTION_TYPE:\n return this.createMarkupSection(tagName, markers);\n default:\n (0, _mobiledocKitUtilsAssert['default'])('Cannot create markerable section of type ' + type, false);\n }\n }\n\n /**\n * @param {tagName} [tagName='P']\n * @param {Marker[]} [markers=[]]\n * @return {MarkupSection}\n */\n }, {\n key: 'createMarkupSection',\n value: function createMarkupSection() {\n var tagName = arguments.length <= 0 || arguments[0] === undefined ? _mobiledocKitModelsMarkupSection.DEFAULT_TAG_NAME : arguments[0];\n var markers = arguments.length <= 1 || arguments[1] === undefined ? [] : arguments[1];\n var isGenerated = arguments.length <= 2 || arguments[2] === undefined ? false : arguments[2];\n\n tagName = (0, _mobiledocKitUtilsDomUtils.normalizeTagName)(tagName);\n var section = new _mobiledocKitModelsMarkupSection['default'](tagName, markers);\n if (isGenerated) {\n section.isGenerated = true;\n }\n section.builder = this;\n return section;\n }\n }, {\n key: 'createListSection',\n value: function createListSection() {\n var tagName = arguments.length <= 0 || arguments[0] === undefined ? _mobiledocKitModelsListSection.DEFAULT_TAG_NAME : arguments[0];\n var items = arguments.length <= 1 || arguments[1] === undefined ? [] : arguments[1];\n\n tagName = (0, _mobiledocKitUtilsDomUtils.normalizeTagName)(tagName);\n var section = new _mobiledocKitModelsListSection['default'](tagName, items);\n section.builder = this;\n return section;\n }\n }, {\n key: 'createListItem',\n value: function createListItem() {\n var markers = arguments.length <= 0 || arguments[0] === undefined ? [] : arguments[0];\n\n var tagName = (0, _mobiledocKitUtilsDomUtils.normalizeTagName)('li');\n var item = new _mobiledocKitModelsListItem['default'](tagName, markers);\n item.builder = this;\n return item;\n }\n }, {\n key: 'createImageSection',\n value: function createImageSection(url) {\n var section = new _mobiledocKitModelsImage['default']();\n if (url) {\n section.src = url;\n }\n return section;\n }\n\n /**\n * @param {String} name\n * @param {Object} [payload={}]\n * @return {CardSection}\n */\n }, {\n key: 'createCardSection',\n value: function createCardSection(name) {\n var payload = arguments.length <= 1 || arguments[1] === undefined ? {} : arguments[1];\n\n var card = new _mobiledocKitModelsCard['default'](name, payload);\n card.builder = this;\n return card;\n }\n\n /**\n * @param {String} value\n * @param {Markup[]} [markups=[]]\n * @return {Marker}\n */\n }, {\n key: 'createMarker',\n value: function createMarker(value) {\n var markups = arguments.length <= 1 || arguments[1] === undefined ? [] : arguments[1];\n\n var marker = new _mobiledocKitModelsMarker['default'](value, markups);\n marker.builder = this;\n return marker;\n }\n\n /**\n * @param {String} name\n * @param {String} [value='']\n * @param {Object} [payload={}]\n * @param {Markup[]} [markups=[]]\n * @return {Atom}\n */\n }, {\n key: 'createAtom',\n value: function createAtom(name) {\n var value = arguments.length <= 1 || arguments[1] === undefined ? '' : arguments[1];\n var payload = arguments.length <= 2 || arguments[2] === undefined ? {} : arguments[2];\n var markups = arguments.length <= 3 || arguments[3] === undefined ? [] : arguments[3];\n\n var atom = new _mobiledocKitModelsAtom['default'](name, value, payload, markups);\n atom.builder = this;\n return atom;\n }\n\n /**\n * @param {String} tagName\n * @param {Object} attributes Key-value pairs of attributes for the markup\n * @return {Markup}\n */\n }, {\n key: 'createMarkup',\n value: function createMarkup(tagName) {\n var attributes = arguments.length <= 1 || arguments[1] === undefined ? {} : arguments[1];\n\n tagName = (0, _mobiledocKitUtilsDomUtils.normalizeTagName)(tagName);\n\n var markup = findMarkupInCache(this.markupCache, tagName, attributes);\n if (!markup) {\n markup = new _mobiledocKitModelsMarkup['default'](tagName, attributes);\n markup.builder = this;\n addMarkupToCache(this.markupCache, markup);\n }\n\n return markup;\n }\n }]);\n\n return PostNodeBuilder;\n })();\n\n exports['default'] = PostNodeBuilder;\n});","define('mobiledoc-kit/models/post', ['exports', 'mobiledoc-kit/models/types', 'mobiledoc-kit/utils/linked-list', 'mobiledoc-kit/utils/array-utils', 'mobiledoc-kit/utils/set', 'mobiledoc-kit/utils/cursor/position', 'mobiledoc-kit/utils/assert'], function (exports, _mobiledocKitModelsTypes, _mobiledocKitUtilsLinkedList, _mobiledocKitUtilsArrayUtils, _mobiledocKitUtilsSet, _mobiledocKitUtilsCursorPosition, _mobiledocKitUtilsAssert) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n /**\n * The Post is an in-memory representation of an editor's document.\n * An editor always has a single post. The post is organized into a list of\n * sections. Each section may be markerable (contains \"markers\", aka editable\n * text) or non-markerable (e.g., a card).\n * When persisting a post, it must first be serialized (loss-lessly) into\n * mobiledoc using {@link Editor#serialize}.\n */\n\n var Post = (function () {\n /**\n * @private\n */\n\n function Post() {\n var _this = this;\n\n _classCallCheck(this, Post);\n\n this.type = _mobiledocKitModelsTypes.POST_TYPE;\n this.sections = new _mobiledocKitUtilsLinkedList['default']({\n adoptItem: function adoptItem(s) {\n return s.post = s.parent = _this;\n },\n freeItem: function freeItem(s) {\n return s.post = s.parent = null;\n }\n });\n }\n\n /**\n * @return {Position} The position at the start of the post (will be a {@link BlankPosition}\n * if the post is blank)\n * @public\n */\n\n _createClass(Post, [{\n key: 'headPosition',\n value: function headPosition() {\n if (this.isBlank) {\n return _mobiledocKitUtilsCursorPosition['default'].blankPosition();\n } else {\n return this.sections.head.headPosition();\n }\n }\n\n /**\n * @return {Position} The position at the end of the post (will be a {@link BlankPosition}\n * if the post is blank)\n * @public\n */\n }, {\n key: 'tailPosition',\n value: function tailPosition() {\n if (this.isBlank) {\n return _mobiledocKitUtilsCursorPosition['default'].blankPosition();\n } else {\n return this.sections.tail.tailPosition();\n }\n }\n\n /**\n * @return {Range} A range encompassing the entire post\n * @public\n */\n }, {\n key: 'toRange',\n value: function toRange() {\n return this.headPosition().toRange(this.tailPosition());\n }\n }, {\n key: 'markersContainedByRange',\n\n /**\n * @param {Range} range\n * @return {Array} markers that are completely contained by the range\n */\n value: function markersContainedByRange(range) {\n var markers = [];\n\n this.walkMarkerableSections(range, function (section) {\n section._markersInRange(range.trimTo(section), function (m, _ref) {\n var isContained = _ref.isContained;\n if (isContained) {\n markers.push(m);\n }\n });\n });\n\n return markers;\n }\n }, {\n key: 'markupsInRange',\n value: function markupsInRange(range) {\n var markups = new _mobiledocKitUtilsSet['default']();\n\n if (range.isCollapsed) {\n var pos = range.head;\n if (pos.isMarkerable) {\n var back = pos.markerIn(-1);\n var forward = pos.markerIn(1);\n\n if (back && forward && back === forward) {\n back.markups.forEach(function (m) {\n return markups.add(m);\n });\n } else {\n (back && back.markups || []).forEach(function (m) {\n if (m.isForwardInclusive()) {\n markups.add(m);\n }\n });\n (forward && forward.markups || []).forEach(function (m) {\n if (m.isBackwardInclusive()) {\n markups.add(m);\n }\n });\n }\n }\n } else {\n this.walkMarkerableSections(range, function (section) {\n (0, _mobiledocKitUtilsArrayUtils.forEach)(section.markupsInRange(range.trimTo(section)), function (m) {\n return markups.add(m);\n });\n });\n }\n\n return markups.toArray();\n }\n }, {\n key: 'walkAllLeafSections',\n value: function walkAllLeafSections(callback) {\n var range = this.headPosition().toRange(this.tailPosition());\n return this.walkLeafSections(range, callback);\n }\n }, {\n key: 'walkLeafSections',\n value: function walkLeafSections(range, callback) {\n var head = range.head;\n var tail = range.tail;\n\n var index = 0;\n var nextSection = undefined,\n shouldStop = undefined;\n var currentSection = head.section;\n\n while (currentSection) {\n nextSection = this._nextLeafSection(currentSection);\n shouldStop = currentSection === tail.section;\n\n callback(currentSection, index);\n index++;\n\n if (shouldStop) {\n break;\n } else {\n currentSection = nextSection;\n }\n }\n }\n }, {\n key: 'walkMarkerableSections',\n value: function walkMarkerableSections(range, callback) {\n this.walkLeafSections(range, function (section) {\n if (section.isMarkerable) {\n callback(section);\n }\n });\n }\n\n // return the next section that has markers after this one,\n // possibly skipping non-markerable sections\n }, {\n key: '_nextLeafSection',\n value: function _nextLeafSection(section) {\n if (!section) {\n return null;\n }\n\n var next = section.next;\n if (next) {\n if (next.isLeafSection) {\n return next;\n } else if (!!next.items) {\n return next.items.head;\n } else {\n (0, _mobiledocKitUtilsAssert['default'])('Cannot determine next section from non-leaf-section', false);\n }\n } else if (section.isNested) {\n // if there is no section after this, but this section is a child\n // (e.g. a ListItem inside a ListSection), check for a markerable\n // section after its parent\n return this._nextLeafSection(section.parent);\n }\n }\n\n /**\n * @param {Range} range\n * @return {Post} A new post, constrained to {range}\n */\n }, {\n key: 'trimTo',\n value: function trimTo(range) {\n var post = this.builder.createPost();\n var builder = this.builder;\n\n var sectionParent = post,\n listParent = null;\n this.walkLeafSections(range, function (section) {\n var newSection = undefined;\n if (section.isMarkerable) {\n if (section.isListItem) {\n if (listParent) {\n sectionParent = null;\n } else {\n listParent = builder.createListSection(section.parent.tagName);\n post.sections.append(listParent);\n sectionParent = null;\n }\n newSection = builder.createListItem();\n listParent.items.append(newSection);\n } else {\n listParent = null;\n sectionParent = post;\n newSection = builder.createMarkupSection(section.tagName);\n }\n\n var currentRange = range.trimTo(section);\n (0, _mobiledocKitUtilsArrayUtils.forEach)(section.markersFor(currentRange.headSectionOffset, currentRange.tailSectionOffset), function (m) {\n return newSection.markers.append(m);\n });\n } else {\n newSection = section.clone();\n }\n if (sectionParent) {\n sectionParent.sections.append(newSection);\n }\n });\n return post;\n }\n }, {\n key: 'isBlank',\n get: function get() {\n return this.sections.isEmpty;\n }\n\n /**\n * If the post has no sections, or only has one, blank section, then it does\n * not have content and this method returns false. Otherwise it is true.\n * @return {Boolean}\n * @public\n */\n }, {\n key: 'hasContent',\n get: function get() {\n if (this.sections.length > 1 || this.sections.length === 1 && !this.sections.head.isBlank) {\n return true;\n } else {\n return false;\n }\n }\n }]);\n\n return Post;\n })();\n\n exports['default'] = Post;\n});","define('mobiledoc-kit/models/render-node', ['exports', 'mobiledoc-kit/utils/linked-item', 'mobiledoc-kit/utils/linked-list', 'mobiledoc-kit/utils/dom-utils', 'mobiledoc-kit/utils/assert'], function (exports, _mobiledocKitUtilsLinkedItem, _mobiledocKitUtilsLinkedList, _mobiledocKitUtilsDomUtils, _mobiledocKitUtilsAssert) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n var _get = function get(_x, _x2, _x3) { var _again = true; _function: while (_again) { var object = _x, property = _x2, receiver = _x3; _again = false; if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { _x = parent; _x2 = property; _x3 = receiver; _again = true; desc = parent = undefined; continue _function; } } else if ('value' in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } } };\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n function _inherits(subClass, superClass) { if (typeof superClass !== 'function' && superClass !== null) { throw new TypeError('Super expression must either be null or a function, not ' + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }\n\n var RenderNode = (function (_LinkedItem) {\n _inherits(RenderNode, _LinkedItem);\n\n function RenderNode(postNode, renderTree) {\n _classCallCheck(this, RenderNode);\n\n _get(Object.getPrototypeOf(RenderNode.prototype), 'constructor', this).call(this);\n this.parent = null;\n this.isDirty = true;\n this.isRemoved = false;\n this.postNode = postNode;\n this._childNodes = null;\n this._element = null;\n this._cursorElement = null; // blank render nodes need a cursor element\n this.renderTree = renderTree;\n\n // RenderNodes for Markers keep track of their markupElement\n this.markupElement = null;\n\n // RenderNodes for Atoms use these properties\n this.headTextNode = null;\n this.tailTextNode = null;\n this.atomNode = null;\n\n // RenderNodes for cards use this property\n this.cardNode = null;\n }\n\n _createClass(RenderNode, [{\n key: 'isAttached',\n value: function isAttached() {\n (0, _mobiledocKitUtilsAssert['default'])('Cannot check if a renderNode is attached without an element.', !!this.element);\n return (0, _mobiledocKitUtilsDomUtils.containsNode)(this.renderTree.rootElement, this.element);\n }\n }, {\n key: 'scheduleForRemoval',\n value: function scheduleForRemoval() {\n this.isRemoved = true;\n if (this.parent) {\n this.parent.markDirty();\n }\n }\n }, {\n key: 'markDirty',\n value: function markDirty() {\n this.isDirty = true;\n if (this.parent) {\n this.parent.markDirty();\n }\n }\n }, {\n key: 'markClean',\n value: function markClean() {\n this.isDirty = false;\n }\n }, {\n key: 'destroy',\n value: function destroy() {\n this.element = null;\n this.parent = null;\n this.postNode = null;\n this.renderTree = null;\n }\n }, {\n key: 'reparsesMutationOfChildNode',\n value: function reparsesMutationOfChildNode(node) {\n if (this.postNode.isCardSection) {\n return !(0, _mobiledocKitUtilsDomUtils.containsNode)(this.cardNode.element, node);\n } else if (this.postNode.isAtom) {\n return !(0, _mobiledocKitUtilsDomUtils.containsNode)(this.atomNode.element, node);\n }\n return true;\n }\n }, {\n key: 'childNodes',\n get: function get() {\n var _this = this;\n\n if (!this._childNodes) {\n this._childNodes = new _mobiledocKitUtilsLinkedList['default']({\n adoptItem: function adoptItem(item) {\n return item.parent = _this;\n },\n freeItem: function freeItem(item) {\n return item.destroy();\n }\n });\n }\n return this._childNodes;\n }\n }, {\n key: 'isRendered',\n get: function get() {\n return !!this.element;\n }\n }, {\n key: 'element',\n set: function set(element) {\n var currentElement = this._element;\n this._element = element;\n\n if (currentElement) {\n this.renderTree.removeElementRenderNode(currentElement);\n }\n\n if (element) {\n this.renderTree.setElementRenderNode(element, this);\n }\n },\n get: function get() {\n return this._element;\n }\n }, {\n key: 'cursorElement',\n set: function set(cursorElement) {\n this._cursorElement = cursorElement;\n },\n get: function get() {\n return this._cursorElement || this.element;\n }\n }]);\n\n return RenderNode;\n })(_mobiledocKitUtilsLinkedItem['default']);\n\n exports['default'] = RenderNode;\n});","define('mobiledoc-kit/models/render-tree', ['exports', 'mobiledoc-kit/models/render-node', 'mobiledoc-kit/utils/element-map'], function (exports, _mobiledocKitModelsRenderNode, _mobiledocKitUtilsElementMap) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n var RenderTree = (function () {\n function RenderTree(rootPostNode) {\n _classCallCheck(this, RenderTree);\n\n this._rootNode = this.buildRenderNode(rootPostNode);\n this._elements = new _mobiledocKitUtilsElementMap['default']();\n }\n\n /*\n * @return {RenderNode} The root render node in this tree\n */\n\n _createClass(RenderTree, [{\n key: 'getElementRenderNode',\n\n /*\n * @param {DOMNode} element\n * @return {RenderNode} The renderNode for this element, if any\n */\n value: function getElementRenderNode(element) {\n return this._elements.get(element);\n }\n }, {\n key: 'setElementRenderNode',\n value: function setElementRenderNode(element, renderNode) {\n this._elements.set(element, renderNode);\n }\n }, {\n key: 'removeElementRenderNode',\n value: function removeElementRenderNode(element) {\n this._elements.remove(element);\n }\n\n /**\n * @param {DOMNode} element\n * Walk up from the dom element until we find a renderNode element\n */\n }, {\n key: 'findRenderNodeFromElement',\n value: function findRenderNodeFromElement(element) {\n var conditionFn = arguments.length <= 1 || arguments[1] === undefined ? function () {\n return true;\n } : arguments[1];\n\n var renderNode = undefined;\n while (element) {\n renderNode = this.getElementRenderNode(element);\n if (renderNode && conditionFn(renderNode)) {\n return renderNode;\n }\n\n // continue loop\n element = element.parentNode;\n\n // stop if we are at the root element\n if (element === this.rootElement) {\n if (conditionFn(this.rootNode)) {\n return this.rootNode;\n } else {\n return;\n }\n }\n }\n }\n }, {\n key: 'buildRenderNode',\n value: function buildRenderNode(postNode) {\n var renderNode = new _mobiledocKitModelsRenderNode['default'](postNode, this);\n postNode.renderNode = renderNode;\n return renderNode;\n }\n }, {\n key: 'rootNode',\n get: function get() {\n return this._rootNode;\n }\n\n /**\n * @return {Boolean}\n */\n }, {\n key: 'isDirty',\n get: function get() {\n return this.rootNode && this.rootNode.isDirty;\n }\n\n /*\n * @return {DOMNode} The root DOM element in this tree\n */\n }, {\n key: 'rootElement',\n get: function get() {\n return this.rootNode.element;\n }\n }]);\n\n return RenderTree;\n })();\n\n exports['default'] = RenderTree;\n});","define('mobiledoc-kit/models/types', ['exports'], function (exports) {\n 'use strict';\n\n var MARKUP_SECTION_TYPE = 'markup-section';\n exports.MARKUP_SECTION_TYPE = MARKUP_SECTION_TYPE;\n var LIST_SECTION_TYPE = 'list-section';\n exports.LIST_SECTION_TYPE = LIST_SECTION_TYPE;\n var MARKUP_TYPE = 'markup';\n exports.MARKUP_TYPE = MARKUP_TYPE;\n var MARKER_TYPE = 'marker';\n exports.MARKER_TYPE = MARKER_TYPE;\n var POST_TYPE = 'post';\n exports.POST_TYPE = POST_TYPE;\n var LIST_ITEM_TYPE = 'list-item';\n exports.LIST_ITEM_TYPE = LIST_ITEM_TYPE;\n var CARD_TYPE = 'card-section';\n exports.CARD_TYPE = CARD_TYPE;\n var IMAGE_SECTION_TYPE = 'image-section';\n exports.IMAGE_SECTION_TYPE = IMAGE_SECTION_TYPE;\n var ATOM_TYPE = 'atom';\n exports.ATOM_TYPE = ATOM_TYPE;\n});","define('mobiledoc-kit/parsers/dom', ['exports', 'mobiledoc-kit/renderers/editor-dom', 'mobiledoc-kit/models/types', 'mobiledoc-kit/utils/dom-utils', 'mobiledoc-kit/utils/array-utils', 'mobiledoc-kit/utils/characters', 'mobiledoc-kit/parsers/section', 'mobiledoc-kit/models/markup'], function (exports, _mobiledocKitRenderersEditorDom, _mobiledocKitModelsTypes, _mobiledocKitUtilsDomUtils, _mobiledocKitUtilsArrayUtils, _mobiledocKitUtilsCharacters, _mobiledocKitParsersSection, _mobiledocKitModelsMarkup) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n exports.transformHTMLText = transformHTMLText;\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n var GOOGLE_DOCS_CONTAINER_ID_REGEX = /^docs\\-internal\\-guid/;\n\n var NO_BREAK_SPACE_REGEX = new RegExp(_mobiledocKitRenderersEditorDom.NO_BREAK_SPACE, 'g');\n var TAB_CHARACTER_REGEX = new RegExp(_mobiledocKitRenderersEditorDom.TAB_CHARACTER, 'g');\n\n function transformHTMLText(textContent) {\n var text = textContent;\n text = text.replace(NO_BREAK_SPACE_REGEX, ' ');\n text = text.replace(TAB_CHARACTER_REGEX, _mobiledocKitUtilsCharacters.TAB);\n return text;\n }\n\n function isGoogleDocsContainer(element) {\n return !(0, _mobiledocKitUtilsDomUtils.isTextNode)(element) && !(0, _mobiledocKitUtilsDomUtils.isCommentNode)(element) && (0, _mobiledocKitUtilsDomUtils.normalizeTagName)(element.tagName) === (0, _mobiledocKitUtilsDomUtils.normalizeTagName)('b') && GOOGLE_DOCS_CONTAINER_ID_REGEX.test(element.id);\n }\n\n function detectRootElement(element) {\n var childNodes = element.childNodes || [];\n var googleDocsContainer = (0, _mobiledocKitUtilsArrayUtils.detect)(childNodes, isGoogleDocsContainer);\n\n if (googleDocsContainer) {\n return googleDocsContainer;\n } else {\n return element;\n }\n }\n\n var TAG_REMAPPING = {\n 'b': 'strong',\n 'i': 'em'\n };\n\n function remapTagName(tagName) {\n var normalized = (0, _mobiledocKitUtilsDomUtils.normalizeTagName)(tagName);\n var remapped = TAG_REMAPPING[normalized];\n return remapped || normalized;\n }\n\n function trim(str) {\n return str.replace(/^\\s+/, '').replace(/\\s+$/, '');\n }\n\n function walkMarkerableNodes(parent, callback) {\n var currentNode = parent;\n\n if ((0, _mobiledocKitUtilsDomUtils.isTextNode)(currentNode) || (0, _mobiledocKitUtilsDomUtils.isElementNode)(currentNode) && currentNode.classList.contains(_mobiledocKitRenderersEditorDom.ATOM_CLASS_NAME)) {\n callback(currentNode);\n } else {\n currentNode = currentNode.firstChild;\n while (currentNode) {\n walkMarkerableNodes(currentNode, callback);\n currentNode = currentNode.nextSibling;\n }\n }\n }\n\n /**\n * Parses DOM element -> Post\n * @private\n */\n\n var DOMParser = (function () {\n function DOMParser(builder) {\n var options = arguments.length <= 1 || arguments[1] === undefined ? {} : arguments[1];\n\n _classCallCheck(this, DOMParser);\n\n this.builder = builder;\n this.sectionParser = new _mobiledocKitParsersSection['default'](this.builder, options);\n }\n\n _createClass(DOMParser, [{\n key: 'parse',\n value: function parse(element) {\n var _this = this;\n\n var post = this.builder.createPost();\n var rootElement = detectRootElement(element);\n\n this._eachChildNode(rootElement, function (child) {\n var sections = _this.parseSections(child);\n _this.appendSections(post, sections);\n });\n\n return post;\n }\n }, {\n key: 'appendSections',\n value: function appendSections(post, sections) {\n var _this2 = this;\n\n (0, _mobiledocKitUtilsArrayUtils.forEach)(sections, function (section) {\n return _this2.appendSection(post, section);\n });\n }\n }, {\n key: 'appendSection',\n value: function appendSection(post, section) {\n if (section.isBlank || section.isMarkerable && trim(section.text) === '') {\n return;\n }\n\n var lastSection = post.sections.tail;\n if (lastSection && lastSection._inferredTagName && section._inferredTagName && lastSection.tagName === section.tagName) {\n lastSection.join(section);\n } else {\n post.sections.append(section);\n }\n }\n }, {\n key: '_eachChildNode',\n value: function _eachChildNode(element, callback) {\n var nodes = (0, _mobiledocKitUtilsDomUtils.isTextNode)(element) ? [element] : element.childNodes;\n (0, _mobiledocKitUtilsArrayUtils.forEach)(nodes, function (node) {\n return callback(node);\n });\n }\n }, {\n key: 'parseSections',\n value: function parseSections(element) {\n return this.sectionParser.parse(element);\n }\n\n // walk up from the textNode until the rootNode, converting each\n // parentNode into a markup\n }, {\n key: 'collectMarkups',\n value: function collectMarkups(textNode, rootNode) {\n var markups = [];\n var currentNode = textNode.parentNode;\n while (currentNode && currentNode !== rootNode) {\n var markup = this.markupFromNode(currentNode);\n if (markup) {\n markups.push(markup);\n }\n\n currentNode = currentNode.parentNode;\n }\n return markups;\n }\n\n // Turn an element node into a markup\n }, {\n key: 'markupFromNode',\n value: function markupFromNode(node) {\n if (_mobiledocKitModelsMarkup['default'].isValidElement(node)) {\n var tagName = remapTagName(node.tagName);\n var attributes = (0, _mobiledocKitUtilsDomUtils.getAttributes)(node);\n return this.builder.createMarkup(tagName, attributes);\n }\n }\n\n // FIXME should move to the section parser?\n // FIXME the `collectMarkups` logic could simplify the section parser?\n }, {\n key: 'reparseSection',\n value: function reparseSection(section, renderTree) {\n switch (section.type) {\n case _mobiledocKitModelsTypes.LIST_SECTION_TYPE:\n return this.reparseListSection(section, renderTree);\n case _mobiledocKitModelsTypes.LIST_ITEM_TYPE:\n return this.reparseListItem(section, renderTree);\n case _mobiledocKitModelsTypes.MARKUP_SECTION_TYPE:\n return this.reparseMarkupSection(section, renderTree);\n default:\n return; // can only parse the above types\n }\n }\n }, {\n key: 'reparseMarkupSection',\n value: function reparseMarkupSection(section, renderTree) {\n return this._reparseSectionContainingMarkers(section, renderTree);\n }\n }, {\n key: 'reparseListItem',\n value: function reparseListItem(listItem, renderTree) {\n return this._reparseSectionContainingMarkers(listItem, renderTree);\n }\n }, {\n key: 'reparseListSection',\n value: function reparseListSection(listSection, renderTree) {\n var _this3 = this;\n\n listSection.items.forEach(function (li) {\n return _this3.reparseListItem(li, renderTree);\n });\n }\n }, {\n key: '_reparseSectionContainingMarkers',\n value: function _reparseSectionContainingMarkers(section, renderTree) {\n var _this4 = this;\n\n var element = section.renderNode.element;\n var seenRenderNodes = [];\n var previousMarker = undefined;\n\n walkMarkerableNodes(element, function (node) {\n var marker = undefined;\n var renderNode = renderTree.getElementRenderNode(node);\n if (renderNode) {\n if (renderNode.postNode.isMarker) {\n var text = transformHTMLText(node.textContent);\n var markups = _this4.collectMarkups(node, element);\n if (text.length) {\n marker = renderNode.postNode;\n marker.value = text;\n marker.markups = markups;\n } else {\n renderNode.scheduleForRemoval();\n }\n } else if (renderNode.postNode.isAtom) {\n var _renderNode = renderNode;\n var headTextNode = _renderNode.headTextNode;\n var tailTextNode = _renderNode.tailTextNode;\n\n if (headTextNode.textContent !== _mobiledocKitRenderersEditorDom.ZWNJ) {\n var value = headTextNode.textContent.replace(new RegExp(_mobiledocKitRenderersEditorDom.ZWNJ, 'g'), '');\n headTextNode.textContent = _mobiledocKitRenderersEditorDom.ZWNJ;\n if (previousMarker && previousMarker.isMarker) {\n previousMarker.value += value;\n if (previousMarker.renderNode) {\n previousMarker.renderNode.markDirty();\n }\n } else {\n var postNode = renderNode.postNode;\n var newMarkups = postNode.markups.slice();\n var newPreviousMarker = _this4.builder.createMarker(value, newMarkups);\n section.markers.insertBefore(newPreviousMarker, postNode);\n\n var newPreviousRenderNode = renderTree.buildRenderNode(newPreviousMarker);\n newPreviousRenderNode.markDirty();\n section.renderNode.markDirty();\n\n seenRenderNodes.push(newPreviousRenderNode);\n section.renderNode.childNodes.insertBefore(newPreviousRenderNode, renderNode);\n }\n }\n if (tailTextNode.textContent !== _mobiledocKitRenderersEditorDom.ZWNJ) {\n var value = tailTextNode.textContent.replace(new RegExp(_mobiledocKitRenderersEditorDom.ZWNJ, 'g'), '');\n tailTextNode.textContent = _mobiledocKitRenderersEditorDom.ZWNJ;\n\n if (renderNode.postNode.next && renderNode.postNode.next.isMarker) {\n var nextMarker = renderNode.postNode.next;\n\n if (nextMarker.renderNode) {\n var nextValue = nextMarker.renderNode.element.textContent;\n nextMarker.renderNode.element.textContent = value + nextValue;\n } else {\n var nextValue = value + nextMarker.value;\n nextMarker.value = nextValue;\n }\n } else {\n var postNode = renderNode.postNode;\n var newMarkups = postNode.markups.slice();\n var newMarker = _this4.builder.createMarker(value, newMarkups);\n\n section.markers.insertAfter(newMarker, postNode);\n\n var newRenderNode = renderTree.buildRenderNode(newMarker);\n seenRenderNodes.push(newRenderNode);\n\n newRenderNode.markDirty();\n section.renderNode.markDirty();\n\n section.renderNode.childNodes.insertAfter(newRenderNode, renderNode);\n }\n }\n if (renderNode) {\n marker = renderNode.postNode;\n }\n }\n } else if ((0, _mobiledocKitUtilsDomUtils.isTextNode)(node)) {\n var text = transformHTMLText(node.textContent);\n var markups = _this4.collectMarkups(node, element);\n marker = _this4.builder.createMarker(text, markups);\n\n renderNode = renderTree.buildRenderNode(marker);\n renderNode.element = node;\n renderNode.markClean();\n section.renderNode.markDirty();\n\n var previousRenderNode = previousMarker && previousMarker.renderNode;\n section.markers.insertAfter(marker, previousMarker);\n section.renderNode.childNodes.insertAfter(renderNode, previousRenderNode);\n }\n\n if (renderNode) {\n seenRenderNodes.push(renderNode);\n }\n previousMarker = marker;\n });\n\n var renderNode = section.renderNode.childNodes.head;\n while (renderNode) {\n if (seenRenderNodes.indexOf(renderNode) === -1) {\n renderNode.scheduleForRemoval();\n }\n renderNode = renderNode.next;\n }\n }\n }]);\n\n return DOMParser;\n })();\n\n exports['default'] = DOMParser;\n});","define('mobiledoc-kit/parsers/html', ['exports', 'mobiledoc-kit/utils/dom-utils', 'mobiledoc-kit/utils/assert', 'mobiledoc-kit/parsers/dom'], function (exports, _mobiledocKitUtilsDomUtils, _mobiledocKitUtilsAssert, _mobiledocKitParsersDom) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n var HTMLParser = (function () {\n function HTMLParser(builder) {\n var options = arguments.length <= 1 || arguments[1] === undefined ? {} : arguments[1];\n\n _classCallCheck(this, HTMLParser);\n\n (0, _mobiledocKitUtilsAssert['default'])('Must pass builder to HTMLParser', builder);\n this.builder = builder;\n this.options = options;\n }\n\n /**\n * @param {String} html to parse\n * @return {Post} A post abstract\n */\n\n _createClass(HTMLParser, [{\n key: 'parse',\n value: function parse(html) {\n var dom = (0, _mobiledocKitUtilsDomUtils.parseHTML)(html);\n var parser = new _mobiledocKitParsersDom['default'](this.builder, this.options);\n return parser.parse(dom);\n }\n }]);\n\n return HTMLParser;\n })();\n\n exports['default'] = HTMLParser;\n});","define('mobiledoc-kit/parsers/mobiledoc/0-2', ['exports', 'mobiledoc-kit/renderers/mobiledoc/0-2', 'mobiledoc-kit/utils/array-utils', 'mobiledoc-kit/utils/assert'], function (exports, _mobiledocKitRenderersMobiledoc02, _mobiledocKitUtilsArrayUtils, _mobiledocKitUtilsAssert) {\n 'use strict';\n\n var _slicedToArray = (function () { function sliceIterator(arr, i) { var _arr = []; var _n = true; var _d = false; var _e = undefined; try { for (var _i = arr[Symbol.iterator](), _s; !(_n = (_s = _i.next()).done); _n = true) { _arr.push(_s.value); if (i && _arr.length === i) break; } } catch (err) { _d = true; _e = err; } finally { try { if (!_n && _i['return']) _i['return'](); } finally { if (_d) throw _e; } } return _arr; } return function (arr, i) { if (Array.isArray(arr)) { return arr; } else if (Symbol.iterator in Object(arr)) { return sliceIterator(arr, i); } else { throw new TypeError('Invalid attempt to destructure non-iterable instance'); } }; })();\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n /*\n * Parses from mobiledoc -> post\n */\n\n var MobiledocParser = (function () {\n function MobiledocParser(builder) {\n _classCallCheck(this, MobiledocParser);\n\n this.builder = builder;\n }\n\n /**\n * @param {Mobiledoc}\n * @return {Post}\n */\n\n _createClass(MobiledocParser, [{\n key: 'parse',\n value: function parse(_ref) {\n var version = _ref.version;\n var sectionData = _ref.sections;\n\n try {\n var markerTypes = sectionData[0];\n var sections = sectionData[1];\n\n var post = this.builder.createPost();\n\n this.markups = [];\n this.markerTypes = this.parseMarkerTypes(markerTypes);\n this.parseSections(sections, post);\n\n return post;\n } catch (e) {\n (0, _mobiledocKitUtilsAssert['default'])('Unable to parse mobiledoc: ' + e.message, false);\n }\n }\n }, {\n key: 'parseMarkerTypes',\n value: function parseMarkerTypes(markerTypes) {\n var _this = this;\n\n return markerTypes.map(function (markerType) {\n return _this.parseMarkerType(markerType);\n });\n }\n }, {\n key: 'parseMarkerType',\n value: function parseMarkerType(_ref2) {\n var _ref22 = _slicedToArray(_ref2, 2);\n\n var tagName = _ref22[0];\n var attributesArray = _ref22[1];\n\n var attributesObject = (0, _mobiledocKitUtilsArrayUtils.kvArrayToObject)(attributesArray || []);\n return this.builder.createMarkup(tagName, attributesObject);\n }\n }, {\n key: 'parseSections',\n value: function parseSections(sections, post) {\n var _this2 = this;\n\n sections.forEach(function (section) {\n return _this2.parseSection(section, post);\n });\n }\n }, {\n key: 'parseSection',\n value: function parseSection(section, post) {\n var _section = _slicedToArray(section, 1);\n\n var type = _section[0];\n\n switch (type) {\n case _mobiledocKitRenderersMobiledoc02.MOBILEDOC_MARKUP_SECTION_TYPE:\n this.parseMarkupSection(section, post);\n break;\n case _mobiledocKitRenderersMobiledoc02.MOBILEDOC_IMAGE_SECTION_TYPE:\n this.parseImageSection(section, post);\n break;\n case _mobiledocKitRenderersMobiledoc02.MOBILEDOC_CARD_SECTION_TYPE:\n this.parseCardSection(section, post);\n break;\n case _mobiledocKitRenderersMobiledoc02.MOBILEDOC_LIST_SECTION_TYPE:\n this.parseListSection(section, post);\n break;\n default:\n (0, _mobiledocKitUtilsAssert['default'])('Unexpected section type ' + type, false);\n }\n }\n }, {\n key: 'parseCardSection',\n value: function parseCardSection(_ref3, post) {\n var _ref32 = _slicedToArray(_ref3, 3);\n\n var type = _ref32[0];\n var name = _ref32[1];\n var payload = _ref32[2];\n\n var section = this.builder.createCardSection(name, payload);\n post.sections.append(section);\n }\n }, {\n key: 'parseImageSection',\n value: function parseImageSection(_ref4, post) {\n var _ref42 = _slicedToArray(_ref4, 2);\n\n var type = _ref42[0];\n var src = _ref42[1];\n\n var section = this.builder.createImageSection(src);\n post.sections.append(section);\n }\n }, {\n key: 'parseMarkupSection',\n value: function parseMarkupSection(_ref5, post) {\n var _ref52 = _slicedToArray(_ref5, 3);\n\n var type = _ref52[0];\n var tagName = _ref52[1];\n var markers = _ref52[2];\n\n var section = this.builder.createMarkupSection(tagName.toLowerCase() === 'pull-quote' ? 'aside' : tagName);\n post.sections.append(section);\n this.parseMarkers(markers, section);\n // Strip blank markers after they have been created. This ensures any\n // markup they include has been correctly populated.\n (0, _mobiledocKitUtilsArrayUtils.filter)(section.markers, function (m) {\n return m.isBlank;\n }).forEach(function (m) {\n section.markers.remove(m);\n });\n }\n }, {\n key: 'parseListSection',\n value: function parseListSection(_ref6, post) {\n var _ref62 = _slicedToArray(_ref6, 3);\n\n var type = _ref62[0];\n var tagName = _ref62[1];\n var items = _ref62[2];\n\n var section = this.builder.createListSection(tagName);\n post.sections.append(section);\n this.parseListItems(items, section);\n }\n }, {\n key: 'parseListItems',\n value: function parseListItems(items, section) {\n var _this3 = this;\n\n items.forEach(function (i) {\n return _this3.parseListItem(i, section);\n });\n }\n }, {\n key: 'parseListItem',\n value: function parseListItem(markers, section) {\n var item = this.builder.createListItem();\n this.parseMarkers(markers, item);\n section.items.append(item);\n }\n }, {\n key: 'parseMarkers',\n value: function parseMarkers(markers, parent) {\n var _this4 = this;\n\n markers.forEach(function (m) {\n return _this4.parseMarker(m, parent);\n });\n }\n }, {\n key: 'parseMarker',\n value: function parseMarker(_ref7, parent) {\n var _this5 = this;\n\n var _ref72 = _slicedToArray(_ref7, 3);\n\n var markerTypeIndexes = _ref72[0];\n var closeCount = _ref72[1];\n var value = _ref72[2];\n\n markerTypeIndexes.forEach(function (index) {\n _this5.markups.push(_this5.markerTypes[index]);\n });\n var marker = this.builder.createMarker(value, this.markups.slice());\n parent.markers.append(marker);\n this.markups = this.markups.slice(0, this.markups.length - closeCount);\n }\n }]);\n\n return MobiledocParser;\n })();\n\n exports['default'] = MobiledocParser;\n});","define('mobiledoc-kit/parsers/mobiledoc/0-3-1', ['exports', 'mobiledoc-kit/renderers/mobiledoc/0-3-1', 'mobiledoc-kit/utils/array-utils', 'mobiledoc-kit/utils/assert'], function (exports, _mobiledocKitRenderersMobiledoc031, _mobiledocKitUtilsArrayUtils, _mobiledocKitUtilsAssert) {\n 'use strict';\n\n var _slicedToArray = (function () { function sliceIterator(arr, i) { var _arr = []; var _n = true; var _d = false; var _e = undefined; try { for (var _i = arr[Symbol.iterator](), _s; !(_n = (_s = _i.next()).done); _n = true) { _arr.push(_s.value); if (i && _arr.length === i) break; } } catch (err) { _d = true; _e = err; } finally { try { if (!_n && _i['return']) _i['return'](); } finally { if (_d) throw _e; } } return _arr; } return function (arr, i) { if (Array.isArray(arr)) { return arr; } else if (Symbol.iterator in Object(arr)) { return sliceIterator(arr, i); } else { throw new TypeError('Invalid attempt to destructure non-iterable instance'); } }; })();\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n /*\n * Parses from mobiledoc -> post\n */\n\n var MobiledocParser = (function () {\n function MobiledocParser(builder) {\n _classCallCheck(this, MobiledocParser);\n\n this.builder = builder;\n }\n\n /**\n * @param {Mobiledoc}\n * @return {Post}\n */\n\n _createClass(MobiledocParser, [{\n key: 'parse',\n value: function parse(_ref) {\n var version = _ref.version;\n var sections = _ref.sections;\n var markerTypes = _ref.markups;\n var cardTypes = _ref.cards;\n var atomTypes = _ref.atoms;\n\n try {\n var post = this.builder.createPost();\n\n this.markups = [];\n this.markerTypes = this.parseMarkerTypes(markerTypes);\n this.cardTypes = this.parseCardTypes(cardTypes);\n this.atomTypes = this.parseAtomTypes(atomTypes);\n this.parseSections(sections, post);\n\n return post;\n } catch (e) {\n (0, _mobiledocKitUtilsAssert['default'])('Unable to parse mobiledoc: ' + e.message, false);\n }\n }\n }, {\n key: 'parseMarkerTypes',\n value: function parseMarkerTypes(markerTypes) {\n var _this = this;\n\n return markerTypes.map(function (markerType) {\n return _this.parseMarkerType(markerType);\n });\n }\n }, {\n key: 'parseMarkerType',\n value: function parseMarkerType(_ref2) {\n var _ref22 = _slicedToArray(_ref2, 2);\n\n var tagName = _ref22[0];\n var attributesArray = _ref22[1];\n\n var attributesObject = (0, _mobiledocKitUtilsArrayUtils.kvArrayToObject)(attributesArray || []);\n return this.builder.createMarkup(tagName, attributesObject);\n }\n }, {\n key: 'parseCardTypes',\n value: function parseCardTypes(cardTypes) {\n var _this2 = this;\n\n return cardTypes.map(function (cardType) {\n return _this2.parseCardType(cardType);\n });\n }\n }, {\n key: 'parseCardType',\n value: function parseCardType(_ref3) {\n var _ref32 = _slicedToArray(_ref3, 2);\n\n var cardName = _ref32[0];\n var cardPayload = _ref32[1];\n\n return [cardName, cardPayload];\n }\n }, {\n key: 'parseAtomTypes',\n value: function parseAtomTypes(atomTypes) {\n var _this3 = this;\n\n return atomTypes.map(function (atomType) {\n return _this3.parseAtomType(atomType);\n });\n }\n }, {\n key: 'parseAtomType',\n value: function parseAtomType(_ref4) {\n var _ref42 = _slicedToArray(_ref4, 3);\n\n var atomName = _ref42[0];\n var atomValue = _ref42[1];\n var atomPayload = _ref42[2];\n\n return [atomName, atomValue, atomPayload];\n }\n }, {\n key: 'parseSections',\n value: function parseSections(sections, post) {\n var _this4 = this;\n\n sections.forEach(function (section) {\n return _this4.parseSection(section, post);\n });\n }\n }, {\n key: 'parseSection',\n value: function parseSection(section, post) {\n var _section = _slicedToArray(section, 1);\n\n var type = _section[0];\n\n switch (type) {\n case _mobiledocKitRenderersMobiledoc031.MOBILEDOC_MARKUP_SECTION_TYPE:\n this.parseMarkupSection(section, post);\n break;\n case _mobiledocKitRenderersMobiledoc031.MOBILEDOC_IMAGE_SECTION_TYPE:\n this.parseImageSection(section, post);\n break;\n case _mobiledocKitRenderersMobiledoc031.MOBILEDOC_CARD_SECTION_TYPE:\n this.parseCardSection(section, post);\n break;\n case _mobiledocKitRenderersMobiledoc031.MOBILEDOC_LIST_SECTION_TYPE:\n this.parseListSection(section, post);\n break;\n default:\n (0, _mobiledocKitUtilsAssert['default'])('Unexpected section type ${type}', false);\n }\n }\n }, {\n key: 'getAtomTypeFromIndex',\n value: function getAtomTypeFromIndex(index) {\n var atomType = this.atomTypes[index];\n (0, _mobiledocKitUtilsAssert['default'])('No atom definition found at index ' + index, !!atomType);\n return atomType;\n }\n }, {\n key: 'getCardTypeFromIndex',\n value: function getCardTypeFromIndex(index) {\n var cardType = this.cardTypes[index];\n (0, _mobiledocKitUtilsAssert['default'])('No card definition found at index ' + index, !!cardType);\n return cardType;\n }\n }, {\n key: 'parseCardSection',\n value: function parseCardSection(_ref5, post) {\n var _ref52 = _slicedToArray(_ref5, 2);\n\n var type = _ref52[0];\n var cardIndex = _ref52[1];\n\n var _getCardTypeFromIndex = this.getCardTypeFromIndex(cardIndex);\n\n var _getCardTypeFromIndex2 = _slicedToArray(_getCardTypeFromIndex, 2);\n\n var name = _getCardTypeFromIndex2[0];\n var payload = _getCardTypeFromIndex2[1];\n\n var section = this.builder.createCardSection(name, payload);\n post.sections.append(section);\n }\n }, {\n key: 'parseImageSection',\n value: function parseImageSection(_ref6, post) {\n var _ref62 = _slicedToArray(_ref6, 2);\n\n var type = _ref62[0];\n var src = _ref62[1];\n\n var section = this.builder.createImageSection(src);\n post.sections.append(section);\n }\n }, {\n key: 'parseMarkupSection',\n value: function parseMarkupSection(_ref7, post) {\n var _ref72 = _slicedToArray(_ref7, 3);\n\n var type = _ref72[0];\n var tagName = _ref72[1];\n var markers = _ref72[2];\n\n var section = this.builder.createMarkupSection(tagName);\n post.sections.append(section);\n this.parseMarkers(markers, section);\n // Strip blank markers after they have been created. This ensures any\n // markup they include has been correctly populated.\n (0, _mobiledocKitUtilsArrayUtils.filter)(section.markers, function (m) {\n return m.isBlank;\n }).forEach(function (m) {\n section.markers.remove(m);\n });\n }\n }, {\n key: 'parseListSection',\n value: function parseListSection(_ref8, post) {\n var _ref82 = _slicedToArray(_ref8, 3);\n\n var type = _ref82[0];\n var tagName = _ref82[1];\n var items = _ref82[2];\n\n var section = this.builder.createListSection(tagName);\n post.sections.append(section);\n this.parseListItems(items, section);\n }\n }, {\n key: 'parseListItems',\n value: function parseListItems(items, section) {\n var _this5 = this;\n\n items.forEach(function (i) {\n return _this5.parseListItem(i, section);\n });\n }\n }, {\n key: 'parseListItem',\n value: function parseListItem(markers, section) {\n var item = this.builder.createListItem();\n this.parseMarkers(markers, item);\n section.items.append(item);\n }\n }, {\n key: 'parseMarkers',\n value: function parseMarkers(markers, parent) {\n var _this6 = this;\n\n markers.forEach(function (m) {\n return _this6.parseMarker(m, parent);\n });\n }\n }, {\n key: 'parseMarker',\n value: function parseMarker(_ref9, parent) {\n var _this7 = this;\n\n var _ref92 = _slicedToArray(_ref9, 4);\n\n var type = _ref92[0];\n var markerTypeIndexes = _ref92[1];\n var closeCount = _ref92[2];\n var value = _ref92[3];\n\n markerTypeIndexes.forEach(function (index) {\n _this7.markups.push(_this7.markerTypes[index]);\n });\n\n var marker = this.buildMarkerType(type, value);\n parent.markers.append(marker);\n\n this.markups = this.markups.slice(0, this.markups.length - closeCount);\n }\n }, {\n key: 'buildMarkerType',\n value: function buildMarkerType(type, value) {\n switch (type) {\n case _mobiledocKitRenderersMobiledoc031.MOBILEDOC_MARKUP_MARKER_TYPE:\n return this.builder.createMarker(value, this.markups.slice());\n case _mobiledocKitRenderersMobiledoc031.MOBILEDOC_ATOM_MARKER_TYPE:\n var _getAtomTypeFromIndex = this.getAtomTypeFromIndex(value),\n _getAtomTypeFromIndex2 = _slicedToArray(_getAtomTypeFromIndex, 3),\n atomName = _getAtomTypeFromIndex2[0],\n atomValue = _getAtomTypeFromIndex2[1],\n atomPayload = _getAtomTypeFromIndex2[2];\n\n return this.builder.createAtom(atomName, atomValue, atomPayload, this.markups.slice());\n default:\n (0, _mobiledocKitUtilsAssert['default'])('Unexpected marker type ' + type, false);\n }\n }\n }]);\n\n return MobiledocParser;\n })();\n\n exports['default'] = MobiledocParser;\n});","define('mobiledoc-kit/parsers/mobiledoc/0-3', ['exports', 'mobiledoc-kit/renderers/mobiledoc/0-3', 'mobiledoc-kit/utils/array-utils', 'mobiledoc-kit/utils/assert'], function (exports, _mobiledocKitRenderersMobiledoc03, _mobiledocKitUtilsArrayUtils, _mobiledocKitUtilsAssert) {\n 'use strict';\n\n var _slicedToArray = (function () { function sliceIterator(arr, i) { var _arr = []; var _n = true; var _d = false; var _e = undefined; try { for (var _i = arr[Symbol.iterator](), _s; !(_n = (_s = _i.next()).done); _n = true) { _arr.push(_s.value); if (i && _arr.length === i) break; } } catch (err) { _d = true; _e = err; } finally { try { if (!_n && _i['return']) _i['return'](); } finally { if (_d) throw _e; } } return _arr; } return function (arr, i) { if (Array.isArray(arr)) { return arr; } else if (Symbol.iterator in Object(arr)) { return sliceIterator(arr, i); } else { throw new TypeError('Invalid attempt to destructure non-iterable instance'); } }; })();\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n /*\n * Parses from mobiledoc -> post\n */\n\n var MobiledocParser = (function () {\n function MobiledocParser(builder) {\n _classCallCheck(this, MobiledocParser);\n\n this.builder = builder;\n }\n\n /**\n * @param {Mobiledoc}\n * @return {Post}\n */\n\n _createClass(MobiledocParser, [{\n key: 'parse',\n value: function parse(_ref) {\n var version = _ref.version;\n var sections = _ref.sections;\n var markerTypes = _ref.markups;\n var cardTypes = _ref.cards;\n var atomTypes = _ref.atoms;\n\n try {\n var post = this.builder.createPost();\n\n this.markups = [];\n this.markerTypes = this.parseMarkerTypes(markerTypes);\n this.cardTypes = this.parseCardTypes(cardTypes);\n this.atomTypes = this.parseAtomTypes(atomTypes);\n this.parseSections(sections, post);\n\n return post;\n } catch (e) {\n (0, _mobiledocKitUtilsAssert['default'])('Unable to parse mobiledoc: ' + e.message, false);\n }\n }\n }, {\n key: 'parseMarkerTypes',\n value: function parseMarkerTypes(markerTypes) {\n var _this = this;\n\n return markerTypes.map(function (markerType) {\n return _this.parseMarkerType(markerType);\n });\n }\n }, {\n key: 'parseMarkerType',\n value: function parseMarkerType(_ref2) {\n var _ref22 = _slicedToArray(_ref2, 2);\n\n var tagName = _ref22[0];\n var attributesArray = _ref22[1];\n\n var attributesObject = (0, _mobiledocKitUtilsArrayUtils.kvArrayToObject)(attributesArray || []);\n return this.builder.createMarkup(tagName, attributesObject);\n }\n }, {\n key: 'parseCardTypes',\n value: function parseCardTypes(cardTypes) {\n var _this2 = this;\n\n return cardTypes.map(function (cardType) {\n return _this2.parseCardType(cardType);\n });\n }\n }, {\n key: 'parseCardType',\n value: function parseCardType(_ref3) {\n var _ref32 = _slicedToArray(_ref3, 2);\n\n var cardName = _ref32[0];\n var cardPayload = _ref32[1];\n\n return [cardName, cardPayload];\n }\n }, {\n key: 'parseAtomTypes',\n value: function parseAtomTypes(atomTypes) {\n var _this3 = this;\n\n return atomTypes.map(function (atomType) {\n return _this3.parseAtomType(atomType);\n });\n }\n }, {\n key: 'parseAtomType',\n value: function parseAtomType(_ref4) {\n var _ref42 = _slicedToArray(_ref4, 3);\n\n var atomName = _ref42[0];\n var atomValue = _ref42[1];\n var atomPayload = _ref42[2];\n\n return [atomName, atomValue, atomPayload];\n }\n }, {\n key: 'parseSections',\n value: function parseSections(sections, post) {\n var _this4 = this;\n\n sections.forEach(function (section) {\n return _this4.parseSection(section, post);\n });\n }\n }, {\n key: 'parseSection',\n value: function parseSection(section, post) {\n var _section = _slicedToArray(section, 1);\n\n var type = _section[0];\n\n switch (type) {\n case _mobiledocKitRenderersMobiledoc03.MOBILEDOC_MARKUP_SECTION_TYPE:\n this.parseMarkupSection(section, post);\n break;\n case _mobiledocKitRenderersMobiledoc03.MOBILEDOC_IMAGE_SECTION_TYPE:\n this.parseImageSection(section, post);\n break;\n case _mobiledocKitRenderersMobiledoc03.MOBILEDOC_CARD_SECTION_TYPE:\n this.parseCardSection(section, post);\n break;\n case _mobiledocKitRenderersMobiledoc03.MOBILEDOC_LIST_SECTION_TYPE:\n this.parseListSection(section, post);\n break;\n default:\n (0, _mobiledocKitUtilsAssert['default'])('Unexpected section type ${type}', false);\n }\n }\n }, {\n key: 'getAtomTypeFromIndex',\n value: function getAtomTypeFromIndex(index) {\n var atomType = this.atomTypes[index];\n (0, _mobiledocKitUtilsAssert['default'])('No atom definition found at index ' + index, !!atomType);\n return atomType;\n }\n }, {\n key: 'getCardTypeFromIndex',\n value: function getCardTypeFromIndex(index) {\n var cardType = this.cardTypes[index];\n (0, _mobiledocKitUtilsAssert['default'])('No card definition found at index ' + index, !!cardType);\n return cardType;\n }\n }, {\n key: 'parseCardSection',\n value: function parseCardSection(_ref5, post) {\n var _ref52 = _slicedToArray(_ref5, 2);\n\n var type = _ref52[0];\n var cardIndex = _ref52[1];\n\n var _getCardTypeFromIndex = this.getCardTypeFromIndex(cardIndex);\n\n var _getCardTypeFromIndex2 = _slicedToArray(_getCardTypeFromIndex, 2);\n\n var name = _getCardTypeFromIndex2[0];\n var payload = _getCardTypeFromIndex2[1];\n\n var section = this.builder.createCardSection(name, payload);\n post.sections.append(section);\n }\n }, {\n key: 'parseImageSection',\n value: function parseImageSection(_ref6, post) {\n var _ref62 = _slicedToArray(_ref6, 2);\n\n var type = _ref62[0];\n var src = _ref62[1];\n\n var section = this.builder.createImageSection(src);\n post.sections.append(section);\n }\n }, {\n key: 'parseMarkupSection',\n value: function parseMarkupSection(_ref7, post) {\n var _ref72 = _slicedToArray(_ref7, 3);\n\n var type = _ref72[0];\n var tagName = _ref72[1];\n var markers = _ref72[2];\n\n var section = this.builder.createMarkupSection(tagName.toLowerCase() === 'pull-quote' ? 'aside' : tagName);\n post.sections.append(section);\n this.parseMarkers(markers, section);\n // Strip blank markers after they have been created. This ensures any\n // markup they include has been correctly populated.\n (0, _mobiledocKitUtilsArrayUtils.filter)(section.markers, function (m) {\n return m.isBlank;\n }).forEach(function (m) {\n section.markers.remove(m);\n });\n }\n }, {\n key: 'parseListSection',\n value: function parseListSection(_ref8, post) {\n var _ref82 = _slicedToArray(_ref8, 3);\n\n var type = _ref82[0];\n var tagName = _ref82[1];\n var items = _ref82[2];\n\n var section = this.builder.createListSection(tagName);\n post.sections.append(section);\n this.parseListItems(items, section);\n }\n }, {\n key: 'parseListItems',\n value: function parseListItems(items, section) {\n var _this5 = this;\n\n items.forEach(function (i) {\n return _this5.parseListItem(i, section);\n });\n }\n }, {\n key: 'parseListItem',\n value: function parseListItem(markers, section) {\n var item = this.builder.createListItem();\n this.parseMarkers(markers, item);\n section.items.append(item);\n }\n }, {\n key: 'parseMarkers',\n value: function parseMarkers(markers, parent) {\n var _this6 = this;\n\n markers.forEach(function (m) {\n return _this6.parseMarker(m, parent);\n });\n }\n }, {\n key: 'parseMarker',\n value: function parseMarker(_ref9, parent) {\n var _this7 = this;\n\n var _ref92 = _slicedToArray(_ref9, 4);\n\n var type = _ref92[0];\n var markerTypeIndexes = _ref92[1];\n var closeCount = _ref92[2];\n var value = _ref92[3];\n\n markerTypeIndexes.forEach(function (index) {\n _this7.markups.push(_this7.markerTypes[index]);\n });\n\n var marker = this.buildMarkerType(type, value);\n parent.markers.append(marker);\n\n this.markups = this.markups.slice(0, this.markups.length - closeCount);\n }\n }, {\n key: 'buildMarkerType',\n value: function buildMarkerType(type, value) {\n switch (type) {\n case _mobiledocKitRenderersMobiledoc03.MOBILEDOC_MARKUP_MARKER_TYPE:\n return this.builder.createMarker(value, this.markups.slice());\n case _mobiledocKitRenderersMobiledoc03.MOBILEDOC_ATOM_MARKER_TYPE:\n var _getAtomTypeFromIndex = this.getAtomTypeFromIndex(value),\n _getAtomTypeFromIndex2 = _slicedToArray(_getAtomTypeFromIndex, 3),\n atomName = _getAtomTypeFromIndex2[0],\n atomValue = _getAtomTypeFromIndex2[1],\n atomPayload = _getAtomTypeFromIndex2[2];\n\n return this.builder.createAtom(atomName, atomValue, atomPayload, this.markups.slice());\n default:\n (0, _mobiledocKitUtilsAssert['default'])('Unexpected marker type ' + type, false);\n }\n }\n }]);\n\n return MobiledocParser;\n })();\n\n exports['default'] = MobiledocParser;\n});","define('mobiledoc-kit/parsers/mobiledoc', ['exports', 'mobiledoc-kit/parsers/mobiledoc/0-2', 'mobiledoc-kit/parsers/mobiledoc/0-3', 'mobiledoc-kit/parsers/mobiledoc/0-3-1', 'mobiledoc-kit/renderers/mobiledoc/0-2', 'mobiledoc-kit/renderers/mobiledoc/0-3', 'mobiledoc-kit/renderers/mobiledoc/0-3-1', 'mobiledoc-kit/utils/assert'], function (exports, _mobiledocKitParsersMobiledoc02, _mobiledocKitParsersMobiledoc03, _mobiledocKitParsersMobiledoc031, _mobiledocKitRenderersMobiledoc02, _mobiledocKitRenderersMobiledoc03, _mobiledocKitRenderersMobiledoc031, _mobiledocKitUtilsAssert) {\n 'use strict';\n\n function parseVersion(mobiledoc) {\n return mobiledoc.version;\n }\n\n exports['default'] = {\n parse: function parse(builder, mobiledoc) {\n var version = parseVersion(mobiledoc);\n switch (version) {\n case _mobiledocKitRenderersMobiledoc02.MOBILEDOC_VERSION:\n return new _mobiledocKitParsersMobiledoc02['default'](builder).parse(mobiledoc);\n case _mobiledocKitRenderersMobiledoc03.MOBILEDOC_VERSION:\n return new _mobiledocKitParsersMobiledoc03['default'](builder).parse(mobiledoc);\n case _mobiledocKitRenderersMobiledoc031.MOBILEDOC_VERSION:\n return new _mobiledocKitParsersMobiledoc031['default'](builder).parse(mobiledoc);\n default:\n (0, _mobiledocKitUtilsAssert['default'])('Unknown version of mobiledoc parser requested: ' + version, false);\n }\n }\n };\n});","define('mobiledoc-kit/parsers/section', ['exports', 'mobiledoc-kit/models/markup-section', 'mobiledoc-kit/models/list-section', 'mobiledoc-kit/models/list-item', 'mobiledoc-kit/models/types', 'mobiledoc-kit/models/markup', 'mobiledoc-kit/utils/dom-utils', 'mobiledoc-kit/utils/array-utils', 'mobiledoc-kit/parsers/dom', 'mobiledoc-kit/utils/assert'], function (exports, _mobiledocKitModelsMarkupSection, _mobiledocKitModelsListSection, _mobiledocKitModelsListItem, _mobiledocKitModelsTypes, _mobiledocKitModelsMarkup, _mobiledocKitUtilsDomUtils, _mobiledocKitUtilsArrayUtils, _mobiledocKitParsersDom, _mobiledocKitUtilsAssert) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _toConsumableArray(arr) { if (Array.isArray(arr)) { for (var i = 0, arr2 = Array(arr.length); i < arr.length; i++) arr2[i] = arr[i]; return arr2; } else { return Array.from(arr); } }\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n var SKIPPABLE_ELEMENT_TAG_NAMES = ['style', 'head', 'title', 'meta'].map(_mobiledocKitUtilsDomUtils.normalizeTagName);\n\n var NEWLINES = /\\n/g;\n function sanitize(text) {\n text = text.replace(NEWLINES, '');\n return text;\n }\n\n /**\n * parses an element into a section, ignoring any non-markup\n * elements contained within\n * @private\n */\n\n var SectionParser = (function () {\n function SectionParser(builder) {\n var options = arguments.length <= 1 || arguments[1] === undefined ? {} : arguments[1];\n\n _classCallCheck(this, SectionParser);\n\n this.builder = builder;\n this.plugins = options.plugins || [];\n }\n\n _createClass(SectionParser, [{\n key: 'parse',\n value: function parse(element) {\n var _this = this;\n\n if (this._isSkippable(element)) {\n return [];\n }\n this.sections = [];\n this.state = {};\n\n this._updateStateFromElement(element);\n\n var childNodes = (0, _mobiledocKitUtilsDomUtils.isTextNode)(element) ? [element] : element.childNodes;\n\n if (this.state.section.isListSection) {\n this.parseListItems(childNodes);\n } else {\n (0, _mobiledocKitUtilsArrayUtils.forEach)(childNodes, function (el) {\n _this.parseNode(el);\n });\n }\n\n this._closeCurrentSection();\n\n return this.sections;\n }\n }, {\n key: 'parseListItems',\n value: function parseListItems(childNodes) {\n var _this2 = this;\n\n var state = this.state;\n\n (0, _mobiledocKitUtilsArrayUtils.forEach)(childNodes, function (el) {\n var parsed = new _this2.constructor(_this2.builder).parse(el);\n var li = parsed[0];\n if (li && li.isListItem) {\n state.section.items.append(li);\n }\n });\n }\n }, {\n key: 'runPlugins',\n value: function runPlugins(node) {\n var _this3 = this;\n\n var isNodeFinished = false;\n var env = {\n addSection: function addSection(section) {\n _this3._closeCurrentSection();\n _this3.sections.push(section);\n },\n addMarkerable: function addMarkerable(marker) {\n var state = _this3.state;\n var section = state.section;\n\n (0, _mobiledocKitUtilsAssert['default'])('Markerables can only be appended to markup sections and list item sections', section && section.isMarkerable);\n if (state.text) {\n _this3._createMarker();\n }\n section.markers.append(marker);\n },\n nodeFinished: function nodeFinished() {\n isNodeFinished = true;\n }\n };\n for (var i = 0; i < this.plugins.length; i++) {\n var plugin = this.plugins[i];\n plugin(node, this.builder, env);\n if (isNodeFinished) {\n return true;\n }\n }\n return false;\n }\n }, {\n key: 'parseNode',\n value: function parseNode(node) {\n if (!this.state.section) {\n this._updateStateFromElement(node);\n }\n\n var nodeFinished = this.runPlugins(node);\n if (nodeFinished) {\n return;\n }\n\n switch (node.nodeType) {\n case _mobiledocKitUtilsDomUtils.NODE_TYPES.TEXT:\n this.parseTextNode(node);\n break;\n case _mobiledocKitUtilsDomUtils.NODE_TYPES.ELEMENT:\n this.parseElementNode(node);\n break;\n }\n }\n }, {\n key: 'parseElementNode',\n value: function parseElementNode(element) {\n var _state$markups,\n _this4 = this;\n\n var state = this.state;\n\n var markups = this._markupsFromElement(element);\n if (markups.length && state.text.length) {\n this._createMarker();\n }\n (_state$markups = state.markups).push.apply(_state$markups, _toConsumableArray(markups));\n\n (0, _mobiledocKitUtilsArrayUtils.forEach)(element.childNodes, function (node) {\n _this4.parseNode(node);\n });\n\n if (markups.length && state.text.length) {\n // create the marker started for this node\n this._createMarker();\n }\n\n // pop the current markups from the stack\n state.markups.splice(-markups.length, markups.length);\n }\n }, {\n key: 'parseTextNode',\n value: function parseTextNode(textNode) {\n var state = this.state;\n\n state.text += sanitize(textNode.textContent);\n }\n }, {\n key: '_updateStateFromElement',\n value: function _updateStateFromElement(element) {\n var state = this.state;\n\n state.section = this._createSectionFromElement(element);\n state.markups = this._markupsFromElement(element);\n state.text = '';\n }\n }, {\n key: '_closeCurrentSection',\n value: function _closeCurrentSection() {\n var sections = this.sections;\n var state = this.state;\n\n if (!state.section) {\n return;\n }\n\n // close a trailing text node if it exists\n if (state.text.length) {\n this._createMarker();\n }\n\n sections.push(state.section);\n state.section = null;\n }\n }, {\n key: '_markupsFromElement',\n value: function _markupsFromElement(element) {\n var builder = this.builder;\n\n var markups = [];\n if ((0, _mobiledocKitUtilsDomUtils.isTextNode)(element)) {\n return markups;\n }\n\n var tagName = (0, _mobiledocKitUtilsDomUtils.normalizeTagName)(element.tagName);\n if (this._isValidMarkupForElement(tagName, element)) {\n markups.push(builder.createMarkup(tagName, (0, _mobiledocKitUtilsDomUtils.getAttributes)(element)));\n }\n\n this._markupsFromElementStyle(element).forEach(function (markup) {\n return markups.push(markup);\n });\n\n return markups;\n }\n }, {\n key: '_isValidMarkupForElement',\n value: function _isValidMarkupForElement(tagName, element) {\n if (_mobiledocKitModelsMarkup.VALID_MARKUP_TAGNAMES.indexOf(tagName) === -1) {\n return false;\n } else if (tagName === 'b') {\n // google docs add a that should not\n // create a \"b\" markup\n return element.style.fontWeight !== 'normal';\n }\n return true;\n }\n }, {\n key: '_markupsFromElementStyle',\n value: function _markupsFromElementStyle(element) {\n var builder = this.builder;\n\n var markups = [];\n var _element$style = element.style;\n var fontStyle = _element$style.fontStyle;\n var fontWeight = _element$style.fontWeight;\n\n if (fontStyle === 'italic') {\n markups.push(builder.createMarkup('em'));\n }\n if (fontWeight === 'bold' || fontWeight === '700') {\n markups.push(builder.createMarkup('strong'));\n }\n return markups;\n }\n }, {\n key: '_createMarker',\n value: function _createMarker() {\n var state = this.state;\n\n var text = (0, _mobiledocKitParsersDom.transformHTMLText)(state.text);\n var marker = this.builder.createMarker(text, state.markups);\n state.section.markers.append(marker);\n state.text = '';\n }\n }, {\n key: '_getSectionDetails',\n value: function _getSectionDetails(element) {\n var sectionType = undefined,\n tagName = undefined,\n inferredTagName = false;\n if ((0, _mobiledocKitUtilsDomUtils.isTextNode)(element)) {\n tagName = _mobiledocKitModelsMarkupSection.DEFAULT_TAG_NAME;\n sectionType = _mobiledocKitModelsTypes.MARKUP_SECTION_TYPE;\n inferredTagName = true;\n } else {\n tagName = (0, _mobiledocKitUtilsDomUtils.normalizeTagName)(element.tagName);\n\n if ((0, _mobiledocKitUtilsArrayUtils.contains)(_mobiledocKitModelsListSection.VALID_LIST_SECTION_TAGNAMES, tagName)) {\n sectionType = _mobiledocKitModelsTypes.LIST_SECTION_TYPE;\n } else if ((0, _mobiledocKitUtilsArrayUtils.contains)(_mobiledocKitModelsListItem.VALID_LIST_ITEM_TAGNAMES, tagName)) {\n sectionType = _mobiledocKitModelsTypes.LIST_ITEM_TYPE;\n } else if ((0, _mobiledocKitUtilsArrayUtils.contains)(_mobiledocKitModelsMarkupSection.VALID_MARKUP_SECTION_TAGNAMES, tagName)) {\n sectionType = _mobiledocKitModelsTypes.MARKUP_SECTION_TYPE;\n } else {\n sectionType = _mobiledocKitModelsTypes.MARKUP_SECTION_TYPE;\n tagName = _mobiledocKitModelsMarkupSection.DEFAULT_TAG_NAME;\n inferredTagName = true;\n }\n }\n\n return { sectionType: sectionType, tagName: tagName, inferredTagName: inferredTagName };\n }\n }, {\n key: '_createSectionFromElement',\n value: function _createSectionFromElement(element) {\n var builder = this.builder;\n\n var section = undefined;\n\n var _getSectionDetails2 = this._getSectionDetails(element);\n\n var tagName = _getSectionDetails2.tagName;\n var sectionType = _getSectionDetails2.sectionType;\n var inferredTagName = _getSectionDetails2.inferredTagName;\n\n switch (sectionType) {\n case _mobiledocKitModelsTypes.LIST_SECTION_TYPE:\n section = builder.createListSection(tagName);\n break;\n case _mobiledocKitModelsTypes.LIST_ITEM_TYPE:\n section = builder.createListItem();\n break;\n case _mobiledocKitModelsTypes.MARKUP_SECTION_TYPE:\n section = builder.createMarkupSection(tagName);\n section._inferredTagName = inferredTagName;\n break;\n default:\n (0, _mobiledocKitUtilsAssert['default'])('Cannot parse section from element', false);\n }\n\n return section;\n }\n }, {\n key: '_isSkippable',\n value: function _isSkippable(element) {\n return (0, _mobiledocKitUtilsDomUtils.isCommentNode)(element) || element.nodeType === _mobiledocKitUtilsDomUtils.NODE_TYPES.ELEMENT && (0, _mobiledocKitUtilsArrayUtils.contains)(SKIPPABLE_ELEMENT_TAG_NAMES, (0, _mobiledocKitUtilsDomUtils.normalizeTagName)(element.tagName));\n }\n }]);\n\n return SectionParser;\n })();\n\n exports['default'] = SectionParser;\n});","define('mobiledoc-kit/parsers/text', ['exports', 'mobiledoc-kit/utils/assert', 'mobiledoc-kit/models/types', 'mobiledoc-kit/models/markup-section'], function (exports, _mobiledocKitUtilsAssert, _mobiledocKitModelsTypes, _mobiledocKitModelsMarkupSection) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n var UL_LI_REGEX = /^\\* (.*)$/;\n var OL_LI_REGEX = /^\\d\\.? (.*)$/;\n var CR = '\\r';\n var LF = '\\n';\n var CR_REGEX = new RegExp(CR, 'g');\n var CR_LF_REGEX = new RegExp(CR + LF, 'g');\n\n var SECTION_BREAK = LF;\n\n exports.SECTION_BREAK = SECTION_BREAK;\n function normalizeLineEndings(text) {\n return text.replace(CR_LF_REGEX, LF).replace(CR_REGEX, LF);\n }\n\n var TextParser = (function () {\n function TextParser(builder, options) {\n _classCallCheck(this, TextParser);\n\n this.builder = builder;\n this.options = options;\n\n this.post = this.builder.createPost();\n this.prevSection = null;\n }\n\n /**\n * @param {String} text to parse\n * @return {Post} a post abstract\n */\n\n _createClass(TextParser, [{\n key: 'parse',\n value: function parse(text) {\n var _this = this;\n\n text = normalizeLineEndings(text);\n text.split(SECTION_BREAK).forEach(function (text) {\n var section = _this._parseSection(text);\n _this._appendSection(section);\n });\n\n return this.post;\n }\n }, {\n key: '_parseSection',\n value: function _parseSection(text) {\n var tagName = _mobiledocKitModelsMarkupSection.DEFAULT_TAG_NAME,\n type = _mobiledocKitModelsTypes.MARKUP_SECTION_TYPE,\n section = undefined;\n\n if (UL_LI_REGEX.test(text)) {\n tagName = 'ul';\n type = _mobiledocKitModelsTypes.LIST_SECTION_TYPE;\n text = text.match(UL_LI_REGEX)[1];\n } else if (OL_LI_REGEX.test(text)) {\n tagName = 'ol';\n type = _mobiledocKitModelsTypes.LIST_SECTION_TYPE;\n text = text.match(OL_LI_REGEX)[1];\n }\n\n var markers = [this.builder.createMarker(text)];\n\n switch (type) {\n case _mobiledocKitModelsTypes.LIST_SECTION_TYPE:\n var item = this.builder.createListItem(markers);\n var list = this.builder.createListSection(tagName, [item]);\n section = list;\n break;\n case _mobiledocKitModelsTypes.MARKUP_SECTION_TYPE:\n section = this.builder.createMarkupSection(tagName, markers);\n break;\n default:\n (0, _mobiledocKitUtilsAssert['default'])('Unknown type encountered ' + type, false);\n }\n\n return section;\n }\n }, {\n key: '_appendSection',\n value: function _appendSection(section) {\n var _this2 = this;\n\n var isSameListSection = section.isListSection && this.prevSection && this.prevSection.isListSection && this.prevSection.tagName === section.tagName;\n\n if (isSameListSection) {\n section.items.forEach(function (item) {\n _this2.prevSection.items.append(item.clone());\n });\n } else {\n this.post.sections.insertAfter(section, this.prevSection);\n this.prevSection = section;\n }\n }\n }]);\n\n return TextParser;\n })();\n\n exports['default'] = TextParser;\n});","define('mobiledoc-kit/renderers/editor-dom', ['exports', 'mobiledoc-kit/models/card-node', 'mobiledoc-kit/utils/array-utils', 'mobiledoc-kit/models/atom-node', 'mobiledoc-kit/models/types', 'mobiledoc-kit/utils/string-utils', 'mobiledoc-kit/utils/dom-utils', 'mobiledoc-kit/models/markup-section', 'mobiledoc-kit/utils/assert', 'mobiledoc-kit/utils/characters'], function (exports, _mobiledocKitModelsCardNode, _mobiledocKitUtilsArrayUtils, _mobiledocKitModelsAtomNode, _mobiledocKitModelsTypes, _mobiledocKitUtilsStringUtils, _mobiledocKitUtilsDomUtils, _mobiledocKitModelsMarkupSection, _mobiledocKitUtilsAssert, _mobiledocKitUtilsCharacters) {\n 'use strict';\n\n var _destroyHooks;\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _defineProperty(obj, key, value) { if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; }\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n var CARD_ELEMENT_CLASS_NAME = '__mobiledoc-card';\n exports.CARD_ELEMENT_CLASS_NAME = CARD_ELEMENT_CLASS_NAME;\n var NO_BREAK_SPACE = ' ';\n exports.NO_BREAK_SPACE = NO_BREAK_SPACE;\n var TAB_CHARACTER = ' ';\n exports.TAB_CHARACTER = TAB_CHARACTER;\n var SPACE = ' ';\n exports.SPACE = SPACE;\n var ZWNJ = '‌';\n exports.ZWNJ = ZWNJ;\n var ATOM_CLASS_NAME = '-mobiledoc-kit__atom';\n exports.ATOM_CLASS_NAME = ATOM_CLASS_NAME;\n var EDITOR_HAS_NO_CONTENT_CLASS_NAME = '__has-no-content';\n exports.EDITOR_HAS_NO_CONTENT_CLASS_NAME = EDITOR_HAS_NO_CONTENT_CLASS_NAME;\n var EDITOR_ELEMENT_CLASS_NAME = '__mobiledoc-editor';\n\n exports.EDITOR_ELEMENT_CLASS_NAME = EDITOR_ELEMENT_CLASS_NAME;\n function createElementFromMarkup(doc, markup) {\n var element = doc.createElement(markup.tagName);\n Object.keys(markup.attributes).forEach(function (k) {\n element.setAttribute(k, markup.attributes[k]);\n });\n return element;\n }\n\n var TWO_SPACES = '' + SPACE + SPACE;\n var SPACE_AND_NO_BREAK = '' + SPACE + NO_BREAK_SPACE;\n var SPACES_REGEX = new RegExp(TWO_SPACES, 'g');\n var TAB_REGEX = new RegExp(_mobiledocKitUtilsCharacters.TAB, 'g');\n var endsWithSpace = function endsWithSpace(text) {\n return (0, _mobiledocKitUtilsStringUtils.endsWith)(text, SPACE);\n };\n var startsWithSpace = function startsWithSpace(text) {\n return (0, _mobiledocKitUtilsStringUtils.startsWith)(text, SPACE);\n };\n\n // FIXME: This can be done more efficiently with a single pass\n // building a correct string based on the original.\n function renderHTMLText(marker) {\n var text = marker.value;\n text = text.replace(SPACES_REGEX, SPACE_AND_NO_BREAK).replace(TAB_REGEX, TAB_CHARACTER);\n\n // If the first marker has a leading space or the last marker has a\n // trailing space, the browser will collapse the space when we position\n // the cursor.\n // See https://github.com/bustle/mobiledoc-kit/issues/68\n // and https://github.com/bustle/mobiledoc-kit/issues/75\n if (marker.isMarker && endsWithSpace(text) && !marker.next) {\n text = text.substr(0, text.length - 1) + NO_BREAK_SPACE;\n }\n if (marker.isMarker && startsWithSpace(text) && (!marker.prev || marker.prev.isMarker && endsWithSpace(marker.prev.value))) {\n text = NO_BREAK_SPACE + text.substr(1);\n }\n return text;\n }\n\n // ascends from element upward, returning the last parent node that is not\n // parentElement\n function penultimateParentOf(element, parentElement) {\n while (parentElement && element.parentNode !== parentElement && element.parentNode !== document.body // ensure the while loop stops\n ) {\n element = element.parentNode;\n }\n return element;\n }\n\n function renderMarkupSection(section) {\n var element = undefined;\n if (_mobiledocKitModelsMarkupSection.MARKUP_SECTION_ELEMENT_NAMES.indexOf(section.tagName) !== -1) {\n element = document.createElement(section.tagName);\n } else {\n element = document.createElement('div');\n (0, _mobiledocKitUtilsDomUtils.addClassName)(element, section.tagName);\n }\n\n return element;\n }\n\n function renderListSection(section) {\n return document.createElement(section.tagName);\n }\n\n function renderListItem() {\n return document.createElement('li');\n }\n\n function renderCursorPlaceholder() {\n return document.createElement('br');\n }\n\n function renderInlineCursorPlaceholder() {\n return document.createTextNode(ZWNJ);\n }\n\n function renderCard() {\n var wrapper = document.createElement('div');\n var cardElement = document.createElement('div');\n cardElement.contentEditable = false;\n (0, _mobiledocKitUtilsDomUtils.addClassName)(cardElement, CARD_ELEMENT_CLASS_NAME);\n wrapper.appendChild(renderInlineCursorPlaceholder());\n wrapper.appendChild(cardElement);\n wrapper.appendChild(renderInlineCursorPlaceholder());\n return { wrapper: wrapper, cardElement: cardElement };\n }\n\n /**\n * Wrap the element in all of the opened markups\n * @return {DOMElement} the wrapped element\n * @private\n */\n function wrapElement(element, openedMarkups) {\n var wrappedElement = element;\n\n for (var i = openedMarkups.length - 1; i >= 0; i--) {\n var markup = openedMarkups[i];\n var openedElement = createElementFromMarkup(document, markup);\n openedElement.appendChild(wrappedElement);\n wrappedElement = openedElement;\n }\n\n return wrappedElement;\n }\n\n // Attach the element to its parent element at the correct position based on the\n // previousRenderNode\n function attachElementToParent(element, parentElement) {\n var previousRenderNode = arguments.length <= 2 || arguments[2] === undefined ? null : arguments[2];\n\n if (previousRenderNode) {\n var previousSibling = previousRenderNode.element;\n var previousSiblingPenultimate = penultimateParentOf(previousSibling, parentElement);\n parentElement.insertBefore(element, previousSiblingPenultimate.nextSibling);\n } else {\n parentElement.insertBefore(element, parentElement.firstChild);\n }\n }\n\n function renderAtom(atom, element, previousRenderNode) {\n var atomElement = document.createElement('span');\n atomElement.contentEditable = false;\n\n var wrapper = document.createElement('span');\n (0, _mobiledocKitUtilsDomUtils.addClassName)(wrapper, ATOM_CLASS_NAME);\n var headTextNode = renderInlineCursorPlaceholder();\n var tailTextNode = renderInlineCursorPlaceholder();\n\n wrapper.appendChild(headTextNode);\n wrapper.appendChild(atomElement);\n wrapper.appendChild(tailTextNode);\n\n var wrappedElement = wrapElement(wrapper, atom.openedMarkups);\n attachElementToParent(wrappedElement, element, previousRenderNode);\n\n return {\n markupElement: wrappedElement,\n wrapper: wrapper,\n atomElement: atomElement,\n headTextNode: headTextNode,\n tailTextNode: tailTextNode\n };\n }\n\n function getNextMarkerElement(renderNode) {\n var element = renderNode.element.parentNode;\n var marker = renderNode.postNode;\n var closedCount = marker.closedMarkups.length;\n\n while (closedCount--) {\n element = element.parentNode;\n }\n return element;\n }\n\n /**\n * Render the marker\n * @param {Marker} marker the marker to render\n * @param {DOMNode} element the element to attach the rendered marker to\n * @param {RenderNode} [previousRenderNode] The render node before this one, which\n * affects the determination of where to insert this rendered marker.\n * @return {Object} With properties `element` and `markupElement`.\n * The element (textNode) that has the text for\n * this marker, and the outermost rendered element. If the marker has no\n * markups, element and markupElement will be the same textNode\n * @private\n */\n function renderMarker(marker, parentElement, previousRenderNode) {\n var text = renderHTMLText(marker);\n\n var element = document.createTextNode(text);\n var markupElement = wrapElement(element, marker.openedMarkups);\n attachElementToParent(markupElement, parentElement, previousRenderNode);\n\n return { element: element, markupElement: markupElement };\n }\n\n // Attach the render node's element to the DOM,\n // replacing the originalElement if it exists\n function attachRenderNodeElementToDOM(renderNode) {\n var originalElement = arguments.length <= 1 || arguments[1] === undefined ? null : arguments[1];\n\n var element = renderNode.element;\n var hasRendered = !!originalElement;\n\n if (hasRendered) {\n var parentElement = renderNode.parent.element;\n parentElement.replaceChild(element, originalElement);\n } else {\n var parentElement = undefined,\n nextSiblingElement = undefined;\n if (renderNode.prev) {\n var previousElement = renderNode.prev.element;\n parentElement = previousElement.parentNode;\n nextSiblingElement = previousElement.nextSibling;\n } else {\n parentElement = renderNode.parent.element;\n nextSiblingElement = parentElement.firstChild;\n }\n parentElement.insertBefore(element, nextSiblingElement);\n }\n }\n\n function removeRenderNodeSectionFromParent(renderNode, section) {\n var parent = renderNode.parent.postNode;\n parent.sections.remove(section);\n }\n\n function removeRenderNodeElementFromParent(renderNode) {\n if (renderNode.element && renderNode.element.parentNode) {\n renderNode.element.parentNode.removeChild(renderNode.element);\n }\n }\n\n function validateCards() {\n var cards = arguments.length <= 0 || arguments[0] === undefined ? [] : arguments[0];\n\n (0, _mobiledocKitUtilsArrayUtils.forEach)(cards, function (card) {\n (0, _mobiledocKitUtilsAssert['default'])('Card \"' + card.name + '\" must define type \"dom\", has: \"' + card.type + '\"', card.type === 'dom');\n (0, _mobiledocKitUtilsAssert['default'])('Card \"' + card.name + '\" must define `render` method', !!card.render);\n });\n return cards;\n }\n\n function validateAtoms() {\n var atoms = arguments.length <= 0 || arguments[0] === undefined ? [] : arguments[0];\n\n (0, _mobiledocKitUtilsArrayUtils.forEach)(atoms, function (atom) {\n (0, _mobiledocKitUtilsAssert['default'])('Atom \"' + atom.name + '\" must define type \"dom\", has: \"' + atom.type + '\"', atom.type === 'dom');\n (0, _mobiledocKitUtilsAssert['default'])('Atom \"' + atom.name + '\" must define `render` method', !!atom.render);\n });\n return atoms;\n }\n\n var Visitor = (function () {\n function Visitor(editor, cards, atoms, unknownCardHandler, unknownAtomHandler, options) {\n _classCallCheck(this, Visitor);\n\n this.editor = editor;\n this.cards = validateCards(cards);\n this.atoms = validateAtoms(atoms);\n this.unknownCardHandler = unknownCardHandler;\n this.unknownAtomHandler = unknownAtomHandler;\n this.options = options;\n }\n\n _createClass(Visitor, [{\n key: '_findCard',\n value: function _findCard(cardName) {\n var card = (0, _mobiledocKitUtilsArrayUtils.detect)(this.cards, function (card) {\n return card.name === cardName;\n });\n return card || this._createUnknownCard(cardName);\n }\n }, {\n key: '_createUnknownCard',\n value: function _createUnknownCard(cardName) {\n (0, _mobiledocKitUtilsAssert['default'])('Unknown card \"' + cardName + '\" found, but no unknownCardHandler is defined', !!this.unknownCardHandler);\n\n return {\n name: cardName,\n type: 'dom',\n render: this.unknownCardHandler,\n edit: this.unknownCardHandler\n };\n }\n }, {\n key: '_findAtom',\n value: function _findAtom(atomName) {\n var atom = (0, _mobiledocKitUtilsArrayUtils.detect)(this.atoms, function (atom) {\n return atom.name === atomName;\n });\n return atom || this._createUnknownAtom(atomName);\n }\n }, {\n key: '_createUnknownAtom',\n value: function _createUnknownAtom(atomName) {\n (0, _mobiledocKitUtilsAssert['default'])('Unknown atom \"' + atomName + '\" found, but no unknownAtomHandler is defined', !!this.unknownAtomHandler);\n\n return {\n name: atomName,\n type: 'dom',\n render: this.unknownAtomHandler\n };\n }\n }, {\n key: _mobiledocKitModelsTypes.POST_TYPE,\n value: function value(renderNode, post, visit) {\n if (!renderNode.element) {\n renderNode.element = document.createElement('div');\n }\n (0, _mobiledocKitUtilsDomUtils.addClassName)(renderNode.element, EDITOR_ELEMENT_CLASS_NAME);\n if (post.hasContent) {\n (0, _mobiledocKitUtilsDomUtils.removeClassName)(renderNode.element, EDITOR_HAS_NO_CONTENT_CLASS_NAME);\n } else {\n (0, _mobiledocKitUtilsDomUtils.addClassName)(renderNode.element, EDITOR_HAS_NO_CONTENT_CLASS_NAME);\n }\n visit(renderNode, post.sections);\n }\n }, {\n key: _mobiledocKitModelsTypes.MARKUP_SECTION_TYPE,\n value: function value(renderNode, section, visit) {\n var originalElement = renderNode.element;\n\n // Always rerender the section -- its tag name or attributes may have changed.\n // TODO make this smarter, only rerendering and replacing the element when necessary\n renderNode.element = renderMarkupSection(section);\n renderNode.cursorElement = null;\n attachRenderNodeElementToDOM(renderNode, originalElement);\n\n if (section.isBlank) {\n var cursorPlaceholder = renderCursorPlaceholder();\n renderNode.element.appendChild(cursorPlaceholder);\n renderNode.cursorElement = cursorPlaceholder;\n } else {\n var visitAll = true;\n visit(renderNode, section.markers, visitAll);\n }\n }\n }, {\n key: _mobiledocKitModelsTypes.LIST_SECTION_TYPE,\n value: function value(renderNode, section, visit) {\n var originalElement = renderNode.element;\n\n renderNode.element = renderListSection(section);\n attachRenderNodeElementToDOM(renderNode, originalElement);\n\n var visitAll = true;\n visit(renderNode, section.items, visitAll);\n }\n }, {\n key: _mobiledocKitModelsTypes.LIST_ITEM_TYPE,\n value: function value(renderNode, item, visit) {\n // FIXME do we need to do anything special for rerenders?\n renderNode.element = renderListItem();\n renderNode.cursorElement = null;\n attachRenderNodeElementToDOM(renderNode, null);\n\n if (item.isBlank) {\n var cursorPlaceholder = renderCursorPlaceholder();\n renderNode.element.appendChild(cursorPlaceholder);\n renderNode.cursorElement = cursorPlaceholder;\n } else {\n var visitAll = true;\n visit(renderNode, item.markers, visitAll);\n }\n }\n }, {\n key: _mobiledocKitModelsTypes.MARKER_TYPE,\n value: function value(renderNode, marker) {\n var parentElement = undefined;\n\n if (renderNode.prev) {\n parentElement = getNextMarkerElement(renderNode.prev);\n } else {\n parentElement = renderNode.parent.element;\n }\n\n var _renderMarker = renderMarker(marker, parentElement, renderNode.prev);\n\n var element = _renderMarker.element;\n var markupElement = _renderMarker.markupElement;\n\n renderNode.element = element;\n renderNode.markupElement = markupElement;\n }\n }, {\n key: _mobiledocKitModelsTypes.IMAGE_SECTION_TYPE,\n value: function value(renderNode, section) {\n if (renderNode.element) {\n if (renderNode.element.src !== section.src) {\n renderNode.element.src = section.src;\n }\n } else {\n var element = document.createElement('img');\n element.src = section.src;\n if (renderNode.prev) {\n var previousElement = renderNode.prev.element;\n var nextElement = previousElement.nextSibling;\n if (nextElement) {\n nextElement.parentNode.insertBefore(element, nextElement);\n }\n }\n if (!element.parentNode) {\n renderNode.parent.element.appendChild(element);\n }\n renderNode.element = element;\n }\n }\n }, {\n key: _mobiledocKitModelsTypes.CARD_TYPE,\n value: function value(renderNode, section) {\n var originalElement = renderNode.element;\n var editor = this.editor;\n var options = this.options;\n\n var card = this._findCard(section.name);\n\n var _renderCard = renderCard();\n\n var wrapper = _renderCard.wrapper;\n var cardElement = _renderCard.cardElement;\n\n renderNode.element = wrapper;\n attachRenderNodeElementToDOM(renderNode, originalElement);\n\n var cardNode = new _mobiledocKitModelsCardNode['default'](editor, card, section, cardElement, options);\n renderNode.cardNode = cardNode;\n\n var initialMode = section._initialMode;\n cardNode[initialMode]();\n }\n }, {\n key: _mobiledocKitModelsTypes.ATOM_TYPE,\n value: function value(renderNode, atomModel) {\n var parentElement = undefined;\n\n if (renderNode.prev) {\n parentElement = getNextMarkerElement(renderNode.prev);\n } else {\n parentElement = renderNode.parent.element;\n }\n\n var editor = this.editor;\n var options = this.options;\n\n var _renderAtom = renderAtom(atomModel, parentElement, renderNode.prev);\n\n var wrapper = _renderAtom.wrapper;\n var markupElement = _renderAtom.markupElement;\n var atomElement = _renderAtom.atomElement;\n var headTextNode = _renderAtom.headTextNode;\n var tailTextNode = _renderAtom.tailTextNode;\n\n var atom = this._findAtom(atomModel.name);\n\n var atomNode = renderNode.atomNode;\n if (!atomNode) {\n // create new AtomNode\n atomNode = new _mobiledocKitModelsAtomNode['default'](editor, atom, atomModel, atomElement, options);\n } else {\n // retarget atomNode to new atom element\n atomNode.element = atomElement;\n }\n\n atomNode.render();\n\n renderNode.atomNode = atomNode;\n renderNode.element = wrapper;\n renderNode.headTextNode = headTextNode;\n renderNode.tailTextNode = tailTextNode;\n renderNode.markupElement = markupElement;\n }\n }]);\n\n return Visitor;\n })();\n\n var destroyHooks = (_destroyHooks = {}, _defineProperty(_destroyHooks, _mobiledocKitModelsTypes.POST_TYPE, function () /*renderNode, post*/{\n (0, _mobiledocKitUtilsAssert['default'])('post destruction is not supported by the renderer', false);\n }), _defineProperty(_destroyHooks, _mobiledocKitModelsTypes.MARKUP_SECTION_TYPE, function (renderNode, section) {\n removeRenderNodeSectionFromParent(renderNode, section);\n removeRenderNodeElementFromParent(renderNode);\n }), _defineProperty(_destroyHooks, _mobiledocKitModelsTypes.LIST_SECTION_TYPE, function (renderNode, section) {\n removeRenderNodeSectionFromParent(renderNode, section);\n removeRenderNodeElementFromParent(renderNode);\n }), _defineProperty(_destroyHooks, _mobiledocKitModelsTypes.LIST_ITEM_TYPE, function (renderNode, li) {\n removeRenderNodeSectionFromParent(renderNode, li);\n removeRenderNodeElementFromParent(renderNode);\n }), _defineProperty(_destroyHooks, _mobiledocKitModelsTypes.MARKER_TYPE, function (renderNode, marker) {\n // FIXME before we render marker, should delete previous renderNode's element\n // and up until the next marker element\n\n // If an atom throws during render we may end up later destroying a renderNode\n // that has not rendered yet, so exit early here if so.\n if (!renderNode.isRendered) {\n return;\n }\n var markupElement = renderNode.markupElement;\n\n if (marker.section) {\n marker.section.markers.remove(marker);\n }\n\n if (markupElement.parentNode) {\n // if no parentNode, the browser already removed this element\n markupElement.parentNode.removeChild(markupElement);\n }\n }), _defineProperty(_destroyHooks, _mobiledocKitModelsTypes.IMAGE_SECTION_TYPE, function (renderNode, section) {\n removeRenderNodeSectionFromParent(renderNode, section);\n removeRenderNodeElementFromParent(renderNode);\n }), _defineProperty(_destroyHooks, _mobiledocKitModelsTypes.CARD_TYPE, function (renderNode, section) {\n if (renderNode.cardNode) {\n renderNode.cardNode.teardown();\n }\n removeRenderNodeSectionFromParent(renderNode, section);\n removeRenderNodeElementFromParent(renderNode);\n }), _defineProperty(_destroyHooks, _mobiledocKitModelsTypes.ATOM_TYPE, function (renderNode, atom) {\n if (renderNode.atomNode) {\n renderNode.atomNode.teardown();\n }\n\n // an atom is a kind of marker so just call its destroy hook vs copying here\n destroyHooks[_mobiledocKitModelsTypes.MARKER_TYPE](renderNode, atom);\n }), _destroyHooks);\n\n // removes children from parentNode (a RenderNode) that are scheduled for removal\n function removeDestroyedChildren(parentNode) {\n var forceRemoval = arguments.length <= 1 || arguments[1] === undefined ? false : arguments[1];\n\n var child = parentNode.childNodes.head;\n var nextChild = undefined,\n method = undefined;\n while (child) {\n nextChild = child.next;\n if (child.isRemoved || forceRemoval) {\n removeDestroyedChildren(child, true);\n method = child.postNode.type;\n (0, _mobiledocKitUtilsAssert['default'])('editor-dom cannot destroy \"' + method + '\"', !!destroyHooks[method]);\n destroyHooks[method](child, child.postNode);\n parentNode.childNodes.remove(child);\n }\n child = nextChild;\n }\n }\n\n // Find an existing render node for the given postNode, or\n // create one, insert it into the tree, and return it\n function lookupNode(renderTree, parentNode, postNode, previousNode) {\n if (postNode.renderNode) {\n return postNode.renderNode;\n } else {\n var renderNode = renderTree.buildRenderNode(postNode);\n parentNode.childNodes.insertAfter(renderNode, previousNode);\n return renderNode;\n }\n }\n\n var Renderer = (function () {\n function Renderer(editor, cards, atoms, unknownCardHandler, unknownAtomHandler, options) {\n _classCallCheck(this, Renderer);\n\n this.editor = editor;\n this.visitor = new Visitor(editor, cards, atoms, unknownCardHandler, unknownAtomHandler, options);\n this.nodes = [];\n this.hasRendered = false;\n }\n\n _createClass(Renderer, [{\n key: 'destroy',\n value: function destroy() {\n if (!this.hasRendered) {\n return;\n }\n var renderNode = this.renderTree.rootNode;\n var force = true;\n removeDestroyedChildren(renderNode, force);\n }\n }, {\n key: 'visit',\n value: function visit(renderTree, parentNode, postNodes) {\n var _this = this;\n\n var visitAll = arguments.length <= 3 || arguments[3] === undefined ? false : arguments[3];\n\n var previousNode = undefined;\n postNodes.forEach(function (postNode) {\n var node = lookupNode(renderTree, parentNode, postNode, previousNode);\n if (node.isDirty || visitAll) {\n _this.nodes.push(node);\n }\n previousNode = node;\n });\n }\n }, {\n key: 'render',\n value: function render(renderTree) {\n var _this2 = this;\n\n this.hasRendered = true;\n this.renderTree = renderTree;\n var renderNode = renderTree.rootNode;\n var method = undefined,\n postNode = undefined;\n\n while (renderNode) {\n removeDestroyedChildren(renderNode);\n postNode = renderNode.postNode;\n\n method = postNode.type;\n (0, _mobiledocKitUtilsAssert['default'])('EditorDom visitor cannot handle type ' + method, !!this.visitor[method]);\n // jshint -W083\n this.visitor[method](renderNode, postNode, function () {\n for (var _len = arguments.length, args = Array(_len), _key = 0; _key < _len; _key++) {\n args[_key] = arguments[_key];\n }\n\n return _this2.visit.apply(_this2, [renderTree].concat(args));\n });\n // jshint +W083\n renderNode.markClean();\n renderNode = this.nodes.shift();\n }\n }\n }]);\n\n return Renderer;\n })();\n\n exports['default'] = Renderer;\n});","define('mobiledoc-kit/renderers/mobiledoc/0-2', ['exports', 'mobiledoc-kit/utils/compiler', 'mobiledoc-kit/utils/array-utils', 'mobiledoc-kit/models/types'], function (exports, _mobiledocKitUtilsCompiler, _mobiledocKitUtilsArrayUtils, _mobiledocKitModelsTypes) {\n 'use strict';\n\n var _visitor;\n\n function _defineProperty(obj, key, value) { if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; }\n\n var MOBILEDOC_VERSION = '0.2.0';\n exports.MOBILEDOC_VERSION = MOBILEDOC_VERSION;\n var MOBILEDOC_MARKUP_SECTION_TYPE = 1;\n exports.MOBILEDOC_MARKUP_SECTION_TYPE = MOBILEDOC_MARKUP_SECTION_TYPE;\n var MOBILEDOC_IMAGE_SECTION_TYPE = 2;\n exports.MOBILEDOC_IMAGE_SECTION_TYPE = MOBILEDOC_IMAGE_SECTION_TYPE;\n var MOBILEDOC_LIST_SECTION_TYPE = 3;\n exports.MOBILEDOC_LIST_SECTION_TYPE = MOBILEDOC_LIST_SECTION_TYPE;\n var MOBILEDOC_CARD_SECTION_TYPE = 10;\n\n exports.MOBILEDOC_CARD_SECTION_TYPE = MOBILEDOC_CARD_SECTION_TYPE;\n var visitor = (_visitor = {}, _defineProperty(_visitor, _mobiledocKitModelsTypes.POST_TYPE, function (node, opcodes) {\n opcodes.push(['openPost']);\n (0, _mobiledocKitUtilsCompiler.visitArray)(visitor, node.sections, opcodes);\n }), _defineProperty(_visitor, _mobiledocKitModelsTypes.MARKUP_SECTION_TYPE, function (node, opcodes) {\n opcodes.push(['openMarkupSection', node.tagName]);\n (0, _mobiledocKitUtilsCompiler.visitArray)(visitor, node.markers, opcodes);\n }), _defineProperty(_visitor, _mobiledocKitModelsTypes.LIST_SECTION_TYPE, function (node, opcodes) {\n opcodes.push(['openListSection', node.tagName]);\n (0, _mobiledocKitUtilsCompiler.visitArray)(visitor, node.items, opcodes);\n }), _defineProperty(_visitor, _mobiledocKitModelsTypes.LIST_ITEM_TYPE, function (node, opcodes) {\n opcodes.push(['openListItem']);\n (0, _mobiledocKitUtilsCompiler.visitArray)(visitor, node.markers, opcodes);\n }), _defineProperty(_visitor, _mobiledocKitModelsTypes.IMAGE_SECTION_TYPE, function (node, opcodes) {\n opcodes.push(['openImageSection', node.src]);\n }), _defineProperty(_visitor, _mobiledocKitModelsTypes.CARD_TYPE, function (node, opcodes) {\n opcodes.push(['openCardSection', node.name, node.payload]);\n }), _defineProperty(_visitor, _mobiledocKitModelsTypes.MARKER_TYPE, function (node, opcodes) {\n opcodes.push(['openMarker', node.closedMarkups.length, node.value]);\n (0, _mobiledocKitUtilsCompiler.visitArray)(visitor, node.openedMarkups, opcodes);\n }), _defineProperty(_visitor, _mobiledocKitModelsTypes.MARKUP_TYPE, function (node, opcodes) {\n opcodes.push(['openMarkup', node.tagName, (0, _mobiledocKitUtilsArrayUtils.objectToSortedKVArray)(node.attributes)]);\n }), _visitor);\n\n var postOpcodeCompiler = {\n openMarker: function openMarker(closeCount, value) {\n this.markupMarkerIds = [];\n this.markers.push([this.markupMarkerIds, closeCount, value || '']);\n },\n openMarkupSection: function openMarkupSection(tagName) {\n this.markers = [];\n this.sections.push([MOBILEDOC_MARKUP_SECTION_TYPE, tagName, this.markers]);\n },\n openListSection: function openListSection(tagName) {\n this.items = [];\n this.sections.push([MOBILEDOC_LIST_SECTION_TYPE, tagName, this.items]);\n },\n openListItem: function openListItem() {\n this.markers = [];\n this.items.push(this.markers);\n },\n openImageSection: function openImageSection(url) {\n this.sections.push([MOBILEDOC_IMAGE_SECTION_TYPE, url]);\n },\n openCardSection: function openCardSection(name, payload) {\n this.sections.push([MOBILEDOC_CARD_SECTION_TYPE, name, payload]);\n },\n openPost: function openPost() {\n this.markerTypes = [];\n this.sections = [];\n this.result = {\n version: MOBILEDOC_VERSION,\n sections: [this.markerTypes, this.sections]\n };\n },\n openMarkup: function openMarkup(tagName, attributes) {\n var index = this._findOrAddMarkerTypeIndex(tagName, attributes);\n this.markupMarkerIds.push(index);\n },\n _findOrAddMarkerTypeIndex: function _findOrAddMarkerTypeIndex(tagName, attributesArray) {\n if (!this._markerTypeCache) {\n this._markerTypeCache = {};\n }\n var key = tagName + '-' + attributesArray.join('-');\n\n var index = this._markerTypeCache[key];\n if (index === undefined) {\n var markerType = [tagName];\n if (attributesArray.length) {\n markerType.push(attributesArray);\n }\n this.markerTypes.push(markerType);\n\n index = this.markerTypes.length - 1;\n this._markerTypeCache[key] = index;\n }\n\n return index;\n }\n };\n\n /**\n * Render from post -> mobiledoc\n */\n exports['default'] = {\n /**\n * @param {Post}\n * @return {Mobiledoc}\n */\n render: function render(post) {\n var opcodes = [];\n (0, _mobiledocKitUtilsCompiler.visit)(visitor, post, opcodes);\n var compiler = Object.create(postOpcodeCompiler);\n (0, _mobiledocKitUtilsCompiler.compile)(compiler, opcodes);\n return compiler.result;\n }\n };\n});","define('mobiledoc-kit/renderers/mobiledoc/0-3-1', ['exports', 'mobiledoc-kit/utils/compiler', 'mobiledoc-kit/utils/array-utils', 'mobiledoc-kit/models/types'], function (exports, _mobiledocKitUtilsCompiler, _mobiledocKitUtilsArrayUtils, _mobiledocKitModelsTypes) {\n 'use strict';\n\n var _visitor;\n\n function _defineProperty(obj, key, value) { if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; }\n\n var MOBILEDOC_VERSION = '0.3.1';\n exports.MOBILEDOC_VERSION = MOBILEDOC_VERSION;\n var MOBILEDOC_MARKUP_SECTION_TYPE = 1;\n exports.MOBILEDOC_MARKUP_SECTION_TYPE = MOBILEDOC_MARKUP_SECTION_TYPE;\n var MOBILEDOC_IMAGE_SECTION_TYPE = 2;\n exports.MOBILEDOC_IMAGE_SECTION_TYPE = MOBILEDOC_IMAGE_SECTION_TYPE;\n var MOBILEDOC_LIST_SECTION_TYPE = 3;\n exports.MOBILEDOC_LIST_SECTION_TYPE = MOBILEDOC_LIST_SECTION_TYPE;\n var MOBILEDOC_CARD_SECTION_TYPE = 10;\n\n exports.MOBILEDOC_CARD_SECTION_TYPE = MOBILEDOC_CARD_SECTION_TYPE;\n var MOBILEDOC_MARKUP_MARKER_TYPE = 0;\n exports.MOBILEDOC_MARKUP_MARKER_TYPE = MOBILEDOC_MARKUP_MARKER_TYPE;\n var MOBILEDOC_ATOM_MARKER_TYPE = 1;\n\n exports.MOBILEDOC_ATOM_MARKER_TYPE = MOBILEDOC_ATOM_MARKER_TYPE;\n var visitor = (_visitor = {}, _defineProperty(_visitor, _mobiledocKitModelsTypes.POST_TYPE, function (node, opcodes) {\n opcodes.push(['openPost']);\n (0, _mobiledocKitUtilsCompiler.visitArray)(visitor, node.sections, opcodes);\n }), _defineProperty(_visitor, _mobiledocKitModelsTypes.MARKUP_SECTION_TYPE, function (node, opcodes) {\n opcodes.push(['openMarkupSection', node.tagName]);\n (0, _mobiledocKitUtilsCompiler.visitArray)(visitor, node.markers, opcodes);\n }), _defineProperty(_visitor, _mobiledocKitModelsTypes.LIST_SECTION_TYPE, function (node, opcodes) {\n opcodes.push(['openListSection', node.tagName]);\n (0, _mobiledocKitUtilsCompiler.visitArray)(visitor, node.items, opcodes);\n }), _defineProperty(_visitor, _mobiledocKitModelsTypes.LIST_ITEM_TYPE, function (node, opcodes) {\n opcodes.push(['openListItem']);\n (0, _mobiledocKitUtilsCompiler.visitArray)(visitor, node.markers, opcodes);\n }), _defineProperty(_visitor, _mobiledocKitModelsTypes.IMAGE_SECTION_TYPE, function (node, opcodes) {\n opcodes.push(['openImageSection', node.src]);\n }), _defineProperty(_visitor, _mobiledocKitModelsTypes.CARD_TYPE, function (node, opcodes) {\n opcodes.push(['openCardSection', node.name, node.payload]);\n }), _defineProperty(_visitor, _mobiledocKitModelsTypes.MARKER_TYPE, function (node, opcodes) {\n opcodes.push(['openMarker', node.closedMarkups.length, node.value]);\n (0, _mobiledocKitUtilsCompiler.visitArray)(visitor, node.openedMarkups, opcodes);\n }), _defineProperty(_visitor, _mobiledocKitModelsTypes.MARKUP_TYPE, function (node, opcodes) {\n opcodes.push(['openMarkup', node.tagName, (0, _mobiledocKitUtilsArrayUtils.objectToSortedKVArray)(node.attributes)]);\n }), _defineProperty(_visitor, _mobiledocKitModelsTypes.ATOM_TYPE, function (node, opcodes) {\n opcodes.push(['openAtom', node.closedMarkups.length, node.name, node.value, node.payload]);\n (0, _mobiledocKitUtilsCompiler.visitArray)(visitor, node.openedMarkups, opcodes);\n }), _visitor);\n\n var postOpcodeCompiler = {\n openMarker: function openMarker(closeCount, value) {\n this.markupMarkerIds = [];\n this.markers.push([MOBILEDOC_MARKUP_MARKER_TYPE, this.markupMarkerIds, closeCount, value || '']);\n },\n openMarkupSection: function openMarkupSection(tagName) {\n this.markers = [];\n this.sections.push([MOBILEDOC_MARKUP_SECTION_TYPE, tagName, this.markers]);\n },\n openListSection: function openListSection(tagName) {\n this.items = [];\n this.sections.push([MOBILEDOC_LIST_SECTION_TYPE, tagName, this.items]);\n },\n openListItem: function openListItem() {\n this.markers = [];\n this.items.push(this.markers);\n },\n openImageSection: function openImageSection(url) {\n this.sections.push([MOBILEDOC_IMAGE_SECTION_TYPE, url]);\n },\n openCardSection: function openCardSection(name, payload) {\n var index = this._addCardTypeIndex(name, payload);\n this.sections.push([MOBILEDOC_CARD_SECTION_TYPE, index]);\n },\n openAtom: function openAtom(closeCount, name, value, payload) {\n var index = this._addAtomTypeIndex(name, value, payload);\n this.markupMarkerIds = [];\n this.markers.push([MOBILEDOC_ATOM_MARKER_TYPE, this.markupMarkerIds, closeCount, index]);\n },\n openPost: function openPost() {\n this.atomTypes = [];\n this.cardTypes = [];\n this.markerTypes = [];\n this.sections = [];\n this.result = {\n version: MOBILEDOC_VERSION,\n atoms: this.atomTypes,\n cards: this.cardTypes,\n markups: this.markerTypes,\n sections: this.sections\n };\n },\n openMarkup: function openMarkup(tagName, attributes) {\n var index = this._findOrAddMarkerTypeIndex(tagName, attributes);\n this.markupMarkerIds.push(index);\n },\n _addCardTypeIndex: function _addCardTypeIndex(cardName, payload) {\n var cardType = [cardName, payload];\n this.cardTypes.push(cardType);\n return this.cardTypes.length - 1;\n },\n _addAtomTypeIndex: function _addAtomTypeIndex(atomName, atomValue, payload) {\n var atomType = [atomName, atomValue, payload];\n this.atomTypes.push(atomType);\n return this.atomTypes.length - 1;\n },\n _findOrAddMarkerTypeIndex: function _findOrAddMarkerTypeIndex(tagName, attributesArray) {\n if (!this._markerTypeCache) {\n this._markerTypeCache = {};\n }\n var key = tagName + '-' + attributesArray.join('-');\n\n var index = this._markerTypeCache[key];\n if (index === undefined) {\n var markerType = [tagName];\n if (attributesArray.length) {\n markerType.push(attributesArray);\n }\n this.markerTypes.push(markerType);\n\n index = this.markerTypes.length - 1;\n this._markerTypeCache[key] = index;\n }\n\n return index;\n }\n };\n\n /**\n * Render from post -> mobiledoc\n */\n exports['default'] = {\n /**\n * @param {Post}\n * @return {Mobiledoc}\n */\n render: function render(post) {\n var opcodes = [];\n (0, _mobiledocKitUtilsCompiler.visit)(visitor, post, opcodes);\n var compiler = Object.create(postOpcodeCompiler);\n (0, _mobiledocKitUtilsCompiler.compile)(compiler, opcodes);\n return compiler.result;\n }\n };\n});","define('mobiledoc-kit/renderers/mobiledoc/0-3', ['exports', 'mobiledoc-kit/utils/compiler', 'mobiledoc-kit/utils/array-utils', 'mobiledoc-kit/models/types'], function (exports, _mobiledocKitUtilsCompiler, _mobiledocKitUtilsArrayUtils, _mobiledocKitModelsTypes) {\n 'use strict';\n\n var _visitor;\n\n function _defineProperty(obj, key, value) { if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; }\n\n var MOBILEDOC_VERSION = '0.3.0';\n exports.MOBILEDOC_VERSION = MOBILEDOC_VERSION;\n var MOBILEDOC_MARKUP_SECTION_TYPE = 1;\n exports.MOBILEDOC_MARKUP_SECTION_TYPE = MOBILEDOC_MARKUP_SECTION_TYPE;\n var MOBILEDOC_IMAGE_SECTION_TYPE = 2;\n exports.MOBILEDOC_IMAGE_SECTION_TYPE = MOBILEDOC_IMAGE_SECTION_TYPE;\n var MOBILEDOC_LIST_SECTION_TYPE = 3;\n exports.MOBILEDOC_LIST_SECTION_TYPE = MOBILEDOC_LIST_SECTION_TYPE;\n var MOBILEDOC_CARD_SECTION_TYPE = 10;\n\n exports.MOBILEDOC_CARD_SECTION_TYPE = MOBILEDOC_CARD_SECTION_TYPE;\n var MOBILEDOC_MARKUP_MARKER_TYPE = 0;\n exports.MOBILEDOC_MARKUP_MARKER_TYPE = MOBILEDOC_MARKUP_MARKER_TYPE;\n var MOBILEDOC_ATOM_MARKER_TYPE = 1;\n\n exports.MOBILEDOC_ATOM_MARKER_TYPE = MOBILEDOC_ATOM_MARKER_TYPE;\n var visitor = (_visitor = {}, _defineProperty(_visitor, _mobiledocKitModelsTypes.POST_TYPE, function (node, opcodes) {\n opcodes.push(['openPost']);\n (0, _mobiledocKitUtilsCompiler.visitArray)(visitor, node.sections, opcodes);\n }), _defineProperty(_visitor, _mobiledocKitModelsTypes.MARKUP_SECTION_TYPE, function (node, opcodes) {\n opcodes.push(['openMarkupSection', node.tagName]);\n (0, _mobiledocKitUtilsCompiler.visitArray)(visitor, node.markers, opcodes);\n }), _defineProperty(_visitor, _mobiledocKitModelsTypes.LIST_SECTION_TYPE, function (node, opcodes) {\n opcodes.push(['openListSection', node.tagName]);\n (0, _mobiledocKitUtilsCompiler.visitArray)(visitor, node.items, opcodes);\n }), _defineProperty(_visitor, _mobiledocKitModelsTypes.LIST_ITEM_TYPE, function (node, opcodes) {\n opcodes.push(['openListItem']);\n (0, _mobiledocKitUtilsCompiler.visitArray)(visitor, node.markers, opcodes);\n }), _defineProperty(_visitor, _mobiledocKitModelsTypes.IMAGE_SECTION_TYPE, function (node, opcodes) {\n opcodes.push(['openImageSection', node.src]);\n }), _defineProperty(_visitor, _mobiledocKitModelsTypes.CARD_TYPE, function (node, opcodes) {\n opcodes.push(['openCardSection', node.name, node.payload]);\n }), _defineProperty(_visitor, _mobiledocKitModelsTypes.MARKER_TYPE, function (node, opcodes) {\n opcodes.push(['openMarker', node.closedMarkups.length, node.value]);\n (0, _mobiledocKitUtilsCompiler.visitArray)(visitor, node.openedMarkups, opcodes);\n }), _defineProperty(_visitor, _mobiledocKitModelsTypes.MARKUP_TYPE, function (node, opcodes) {\n opcodes.push(['openMarkup', node.tagName, (0, _mobiledocKitUtilsArrayUtils.objectToSortedKVArray)(node.attributes)]);\n }), _defineProperty(_visitor, _mobiledocKitModelsTypes.ATOM_TYPE, function (node, opcodes) {\n opcodes.push(['openAtom', node.closedMarkups.length, node.name, node.value, node.payload]);\n (0, _mobiledocKitUtilsCompiler.visitArray)(visitor, node.openedMarkups, opcodes);\n }), _visitor);\n\n var postOpcodeCompiler = {\n openMarker: function openMarker(closeCount, value) {\n this.markupMarkerIds = [];\n this.markers.push([MOBILEDOC_MARKUP_MARKER_TYPE, this.markupMarkerIds, closeCount, value || '']);\n },\n openMarkupSection: function openMarkupSection(tagName) {\n this.markers = [];\n this.sections.push([MOBILEDOC_MARKUP_SECTION_TYPE, tagName, this.markers]);\n },\n openListSection: function openListSection(tagName) {\n this.items = [];\n this.sections.push([MOBILEDOC_LIST_SECTION_TYPE, tagName, this.items]);\n },\n openListItem: function openListItem() {\n this.markers = [];\n this.items.push(this.markers);\n },\n openImageSection: function openImageSection(url) {\n this.sections.push([MOBILEDOC_IMAGE_SECTION_TYPE, url]);\n },\n openCardSection: function openCardSection(name, payload) {\n var index = this._addCardTypeIndex(name, payload);\n this.sections.push([MOBILEDOC_CARD_SECTION_TYPE, index]);\n },\n openAtom: function openAtom(closeCount, name, value, payload) {\n var index = this._addAtomTypeIndex(name, value, payload);\n this.markupMarkerIds = [];\n this.markers.push([MOBILEDOC_ATOM_MARKER_TYPE, this.markupMarkerIds, closeCount, index]);\n },\n openPost: function openPost() {\n this.atomTypes = [];\n this.cardTypes = [];\n this.markerTypes = [];\n this.sections = [];\n this.result = {\n version: MOBILEDOC_VERSION,\n atoms: this.atomTypes,\n cards: this.cardTypes,\n markups: this.markerTypes,\n sections: this.sections\n };\n },\n openMarkup: function openMarkup(tagName, attributes) {\n var index = this._findOrAddMarkerTypeIndex(tagName, attributes);\n this.markupMarkerIds.push(index);\n },\n _addCardTypeIndex: function _addCardTypeIndex(cardName, payload) {\n var cardType = [cardName, payload];\n this.cardTypes.push(cardType);\n return this.cardTypes.length - 1;\n },\n _addAtomTypeIndex: function _addAtomTypeIndex(atomName, atomValue, payload) {\n var atomType = [atomName, atomValue, payload];\n this.atomTypes.push(atomType);\n return this.atomTypes.length - 1;\n },\n _findOrAddMarkerTypeIndex: function _findOrAddMarkerTypeIndex(tagName, attributesArray) {\n if (!this._markerTypeCache) {\n this._markerTypeCache = {};\n }\n var key = tagName + '-' + attributesArray.join('-');\n\n var index = this._markerTypeCache[key];\n if (index === undefined) {\n var markerType = [tagName];\n if (attributesArray.length) {\n markerType.push(attributesArray);\n }\n this.markerTypes.push(markerType);\n\n index = this.markerTypes.length - 1;\n this._markerTypeCache[key] = index;\n }\n\n return index;\n }\n };\n\n /**\n * Render from post -> mobiledoc\n */\n exports['default'] = {\n /**\n * @param {Post}\n * @return {Mobiledoc}\n */\n render: function render(post) {\n var opcodes = [];\n (0, _mobiledocKitUtilsCompiler.visit)(visitor, post, opcodes);\n var compiler = Object.create(postOpcodeCompiler);\n (0, _mobiledocKitUtilsCompiler.compile)(compiler, opcodes);\n return compiler.result;\n }\n };\n});","define('mobiledoc-kit/renderers/mobiledoc', ['exports', 'mobiledoc-kit/renderers/mobiledoc/0-2', 'mobiledoc-kit/renderers/mobiledoc/0-3', 'mobiledoc-kit/renderers/mobiledoc/0-3-1', 'mobiledoc-kit/utils/assert'], function (exports, _mobiledocKitRenderersMobiledoc02, _mobiledocKitRenderersMobiledoc03, _mobiledocKitRenderersMobiledoc031, _mobiledocKitUtilsAssert) {\n 'use strict';\n\n var MOBILEDOC_VERSION = _mobiledocKitRenderersMobiledoc031.MOBILEDOC_VERSION;\n\n exports.MOBILEDOC_VERSION = MOBILEDOC_VERSION;\n exports['default'] = {\n render: function render(post, version) {\n switch (version) {\n case _mobiledocKitRenderersMobiledoc02.MOBILEDOC_VERSION:\n return _mobiledocKitRenderersMobiledoc02['default'].render(post);\n case _mobiledocKitRenderersMobiledoc03.MOBILEDOC_VERSION:\n return _mobiledocKitRenderersMobiledoc03['default'].render(post);\n case undefined:\n case null:\n case _mobiledocKitRenderersMobiledoc031.MOBILEDOC_VERSION:\n return _mobiledocKitRenderersMobiledoc031['default'].render(post);\n default:\n (0, _mobiledocKitUtilsAssert['default'])('Unknown version of mobiledoc renderer requested: ' + version, false);\n }\n }\n };\n});","define(\"mobiledoc-kit/utils/array-utils\", [\"exports\"], function (exports) {\n \"use strict\";\n\n function detect(enumerable, callback) {\n if (enumerable.detect) {\n return enumerable.detect(callback);\n } else {\n for (var i = 0; i < enumerable.length; i++) {\n if (callback(enumerable[i])) {\n return enumerable[i];\n }\n }\n }\n }\n\n function any(enumerable, callback) {\n if (enumerable.any) {\n return enumerable.any(callback);\n }\n\n for (var i = 0; i < enumerable.length; i++) {\n if (callback(enumerable[i])) {\n return true;\n }\n }\n\n return false;\n }\n\n function every(enumerable, callback) {\n if (enumerable.every) {\n return enumerable.every(callback);\n }\n\n for (var i = 0; i < enumerable.length; i++) {\n if (!callback(enumerable[i])) {\n return false;\n }\n }\n return true;\n }\n\n function toArray(arrayLike) {\n return Array.prototype.slice.call(arrayLike);\n }\n\n /**\n * Useful for array-like things that aren't\n * actually arrays, like NodeList\n * @private\n */\n function forEach(enumerable, callback) {\n if (enumerable.forEach) {\n enumerable.forEach(callback);\n } else {\n for (var i = 0; i < enumerable.length; i++) {\n callback(enumerable[i], i);\n }\n }\n }\n\n function filter(enumerable, conditionFn) {\n var filtered = [];\n forEach(enumerable, function (i) {\n if (conditionFn(i)) {\n filtered.push(i);\n }\n });\n return filtered;\n }\n\n /**\n * @return {Integer} the number of items that are the same, starting from the 0th index, in a and b\n * @private\n */\n function commonItemLength(listA, listB) {\n var offset = 0;\n while (offset < listA.length && offset < listB.length) {\n if (listA[offset] !== listB[offset]) {\n break;\n }\n offset++;\n }\n return offset;\n }\n\n /**\n * @return {Array} the items that are the same, starting from the 0th index, in a and b\n * @private\n */\n function commonItems(listA, listB) {\n var offset = 0;\n while (offset < listA.length && offset < listB.length) {\n if (listA[offset] !== listB[offset]) {\n break;\n }\n offset++;\n }\n return listA.slice(0, offset);\n }\n\n // return new array without falsy items like ruby's `compact`\n function compact(enumerable) {\n return filter(enumerable, function (i) {\n return !!i;\n });\n }\n\n function reduce(enumerable, callback, initialValue) {\n var previousValue = initialValue;\n forEach(enumerable, function (val, index) {\n previousValue = callback(previousValue, val, index);\n });\n return previousValue;\n }\n\n /**\n * @param {Array} array of key1,value1,key2,value2,...\n * @return {Object} {key1:value1, key2:value2, ...}\n * @private\n */\n function kvArrayToObject(array) {\n var obj = {};\n for (var i = 0; i < array.length; i += 2) {\n var key = array[i];\n var value = array[i + 1];\n\n obj[key] = value;\n }\n return obj;\n }\n\n function objectToSortedKVArray(obj) {\n var keys = Object.keys(obj).sort();\n var result = [];\n keys.forEach(function (k) {\n result.push(k);\n result.push(obj[k]);\n });\n return result;\n }\n\n // check shallow equality of two non-nested arrays\n function isArrayEqual(arr1, arr2) {\n var l1 = arr1.length,\n l2 = arr2.length;\n if (l1 !== l2) {\n return false;\n }\n\n for (var i = 0; i < l1; i++) {\n if (arr1[i] !== arr2[i]) {\n return false;\n }\n }\n return true;\n }\n\n // return an object with only the valid keys\n function filterObject(object) {\n var validKeys = arguments.length <= 1 || arguments[1] === undefined ? [] : arguments[1];\n\n var result = {};\n forEach(filter(Object.keys(object), function (key) {\n return validKeys.indexOf(key) !== -1;\n }), function (key) {\n return result[key] = object[key];\n });\n return result;\n }\n\n function contains(array, item) {\n return array.indexOf(item) !== -1;\n }\n\n function values(object) {\n return Object.keys(object).map(function (key) {\n return object[key];\n });\n }\n\n exports.detect = detect;\n exports.forEach = forEach;\n exports.any = any;\n exports.every = every;\n exports.filter = filter;\n exports.commonItemLength = commonItemLength;\n exports.commonItems = commonItems;\n exports.compact = compact;\n exports.reduce = reduce;\n exports.objectToSortedKVArray = objectToSortedKVArray;\n exports.kvArrayToObject = kvArrayToObject;\n exports.isArrayEqual = isArrayEqual;\n exports.toArray = toArray;\n exports.filterObject = filterObject;\n exports.contains = contains;\n exports.values = values;\n});","define('mobiledoc-kit/utils/assert', ['exports', 'mobiledoc-kit/utils/mobiledoc-error'], function (exports, _mobiledocKitUtilsMobiledocError) {\n 'use strict';\n\n exports['default'] = function (message, conditional) {\n if (!conditional) {\n throw new _mobiledocKitUtilsMobiledocError['default'](message);\n }\n };\n});","define('mobiledoc-kit/utils/browser', ['exports'], function (exports) {\n 'use strict';\n\n exports['default'] = {\n isMac: function isMac() {\n return typeof window !== 'undefined' && window.navigator && /Mac/.test(window.navigator.platform);\n },\n isWin: function isWin() {\n return typeof window !== 'undefined' && window.navigator && /Win/.test(window.navigator.platform);\n }\n };\n});","define('mobiledoc-kit/utils/characters', ['exports'], function (exports) {\n 'use strict';\n\n var TAB = '\\t';\n exports.TAB = TAB;\n var ENTER = '\\n';\n exports.ENTER = ENTER;\n var SPACE = ' ';\n exports.SPACE = SPACE;\n});","define('mobiledoc-kit/utils/compiler', ['exports', 'mobiledoc-kit/utils/array-utils', 'mobiledoc-kit/utils/assert'], function (exports, _mobiledocKitUtilsArrayUtils, _mobiledocKitUtilsAssert) {\n 'use strict';\n\n exports.visit = visit;\n exports.compile = compile;\n exports.visitArray = visitArray;\n\n function _toArray(arr) { return Array.isArray(arr) ? arr : Array.from(arr); }\n\n function visit(visitor, node, opcodes) {\n var method = node.type;\n (0, _mobiledocKitUtilsAssert['default'])('Cannot visit unknown type ' + method, !!visitor[method]);\n visitor[method](node, opcodes);\n }\n\n function compile(compiler, opcodes) {\n for (var i = 0, l = opcodes.length; i < l; i++) {\n var _opcodes$i = _toArray(opcodes[i]);\n\n var method = _opcodes$i[0];\n\n var params = _opcodes$i.slice(1);\n\n var _length = params.length;\n if (_length === 0) {\n compiler[method].call(compiler);\n } else if (_length === 1) {\n compiler[method].call(compiler, params[0]);\n } else if (_length === 2) {\n compiler[method].call(compiler, params[0], params[1]);\n } else {\n compiler[method].apply(compiler, params);\n }\n }\n }\n\n function visitArray(visitor, nodes, opcodes) {\n if (!nodes || nodes.length === 0) {\n return;\n }\n (0, _mobiledocKitUtilsArrayUtils.forEach)(nodes, function (node) {\n visit(visitor, node, opcodes);\n });\n }\n});","define(\"mobiledoc-kit/utils/copy\", [\"exports\"], function (exports) {\n \"use strict\";\n\n function shallowCopyObject(object) {\n var copy = {};\n Object.keys(object).forEach(function (key) {\n copy[key] = object[key];\n });\n return copy;\n }\n\n exports.shallowCopyObject = shallowCopyObject;\n});","define('mobiledoc-kit/utils/cursor', ['exports', 'mobiledoc-kit/utils/selection-utils', 'mobiledoc-kit/utils/dom-utils', 'mobiledoc-kit/utils/cursor/position', 'mobiledoc-kit/utils/cursor/range', 'mobiledoc-kit/utils/key'], function (exports, _mobiledocKitUtilsSelectionUtils, _mobiledocKitUtilsDomUtils, _mobiledocKitUtilsCursorPosition, _mobiledocKitUtilsCursorRange, _mobiledocKitUtilsKey) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n exports.Position = _mobiledocKitUtilsCursorPosition['default'];\n exports.Range = _mobiledocKitUtilsCursorRange['default'];\n\n var Cursor = (function () {\n function Cursor(editor) {\n _classCallCheck(this, Cursor);\n\n this.editor = editor;\n this.renderTree = editor._renderTree;\n this.post = editor.post;\n }\n\n _createClass(Cursor, [{\n key: 'clearSelection',\n value: function clearSelection() {\n (0, _mobiledocKitUtilsSelectionUtils.clearSelection)();\n }\n\n /**\n * @return {Boolean} true when there is either a collapsed cursor in the\n * editor's element or a selection that is contained in the editor's element\n */\n }, {\n key: 'hasCursor',\n value: function hasCursor() {\n return this.editor.hasRendered && (this._hasCollapsedSelection() || this._hasSelection());\n }\n }, {\n key: 'hasSelection',\n value: function hasSelection() {\n return this.editor.hasRendered && this._hasSelection();\n }\n\n /**\n * @return {Boolean} Can the cursor be on this element?\n */\n }, {\n key: 'isAddressable',\n value: function isAddressable(element) {\n var renderTree = this.renderTree;\n\n var renderNode = renderTree.findRenderNodeFromElement(element);\n if (renderNode && renderNode.postNode.isCardSection) {\n var renderedElement = renderNode.element;\n\n // card sections have addressable text nodes containing ‌\n // as their first and last child\n if (element !== renderedElement && element !== renderedElement.firstChild && element !== renderedElement.lastChild) {\n return false;\n }\n }\n\n return !!renderNode;\n }\n\n /*\n * @return {Range} Cursor#Range object\n */\n }, {\n key: '_findNodeForPosition',\n value: function _findNodeForPosition(position) {\n var section = position.section;\n\n var node = undefined,\n offset = undefined;\n if (section.isCardSection) {\n offset = 0;\n if (position.offset === 0) {\n node = section.renderNode.element.firstChild;\n } else {\n node = section.renderNode.element.lastChild;\n }\n } else if (section.isBlank) {\n node = section.renderNode.cursorElement;\n offset = 0;\n } else {\n var marker = position.marker;\n var offsetInMarker = position.offsetInMarker;\n\n if (marker.isAtom) {\n if (offsetInMarker > 0) {\n // FIXME -- if there is a next marker, focus on it?\n offset = 0;\n node = marker.renderNode.tailTextNode;\n } else {\n offset = 0;\n node = marker.renderNode.headTextNode;\n }\n } else {\n node = marker.renderNode.element;\n offset = offsetInMarker;\n }\n }\n\n return { node: node, offset: offset };\n }\n }, {\n key: 'selectRange',\n value: function selectRange(range) {\n if (range.isBlank) {\n this.clearSelection();\n return;\n }\n\n var head = range.head;\n var tail = range.tail;\n var direction = range.direction;\n\n var _findNodeForPosition2 = this._findNodeForPosition(head);\n\n var headNode = _findNodeForPosition2.node;\n var headOffset = _findNodeForPosition2.offset;\n\n var _findNodeForPosition3 = this._findNodeForPosition(tail);\n\n var tailNode = _findNodeForPosition3.node;\n var tailOffset = _findNodeForPosition3.offset;\n\n this._moveToNode(headNode, headOffset, tailNode, tailOffset, direction);\n\n // Firefox sometimes doesn't keep focus in the editor after adding a card\n this.editor._ensureFocus();\n }\n }, {\n key: 'selectedText',\n value: function selectedText() {\n // FIXME remove this\n return this.selection.toString();\n }\n\n /**\n * @param {textNode} node\n * @param {integer} offset\n * @param {textNode} endNode\n * @param {integer} endOffset\n * @param {integer} direction forward or backward, default forward\n * @private\n */\n }, {\n key: '_moveToNode',\n value: function _moveToNode(node, offset, endNode, endOffset) {\n var direction = arguments.length <= 4 || arguments[4] === undefined ? _mobiledocKitUtilsKey.DIRECTION.FORWARD : arguments[4];\n\n this.clearSelection();\n\n if (direction === _mobiledocKitUtilsKey.DIRECTION.BACKWARD) {\n var _ref = [endNode, endOffset, node, offset];\n node = _ref[0];\n offset = _ref[1];\n endNode = _ref[2];\n endOffset = _ref[3];\n }\n\n var range = document.createRange();\n range.setStart(node, offset);\n if (direction === _mobiledocKitUtilsKey.DIRECTION.BACKWARD && !!this.selection.extend) {\n this.selection.addRange(range);\n this.selection.extend(endNode, endOffset);\n } else {\n range.setEnd(endNode, endOffset);\n this.selection.addRange(range);\n }\n }\n }, {\n key: '_hasSelection',\n value: function _hasSelection() {\n var element = this.editor.element;\n var _selectionRange = this._selectionRange;\n\n if (!_selectionRange || _selectionRange.collapsed) {\n return false;\n }\n\n return (0, _mobiledocKitUtilsDomUtils.containsNode)(element, this.selection.anchorNode) && (0, _mobiledocKitUtilsDomUtils.containsNode)(element, this.selection.focusNode);\n }\n }, {\n key: '_hasCollapsedSelection',\n value: function _hasCollapsedSelection() {\n var _selectionRange = this._selectionRange;\n\n if (!_selectionRange) {\n return false;\n }\n\n var element = this.editor.element;\n return (0, _mobiledocKitUtilsDomUtils.containsNode)(element, this.selection.anchorNode);\n }\n }, {\n key: 'offsets',\n get: function get() {\n if (!this.hasCursor()) {\n return _mobiledocKitUtilsCursorRange['default'].blankRange();\n }\n\n var selection = this.selection;\n var renderTree = this.renderTree;\n\n var parentNode = this.editor.element;\n selection = (0, _mobiledocKitUtilsSelectionUtils.constrainSelectionTo)(selection, parentNode);\n\n var _comparePosition = (0, _mobiledocKitUtilsSelectionUtils.comparePosition)(selection);\n\n var headNode = _comparePosition.headNode;\n var headOffset = _comparePosition.headOffset;\n var tailNode = _comparePosition.tailNode;\n var tailOffset = _comparePosition.tailOffset;\n var direction = _comparePosition.direction;\n\n var headPosition = _mobiledocKitUtilsCursorPosition['default'].fromNode(renderTree, headNode, headOffset);\n var tailPosition = _mobiledocKitUtilsCursorPosition['default'].fromNode(renderTree, tailNode, tailOffset);\n\n return new _mobiledocKitUtilsCursorRange['default'](headPosition, tailPosition, direction);\n }\n }, {\n key: 'selection',\n get: function get() {\n return window.getSelection();\n }\n }, {\n key: '_selectionRange',\n get: function get() {\n var selection = this.selection;\n\n if (selection.rangeCount === 0) {\n return null;\n }\n return selection.getRangeAt(0);\n }\n }]);\n\n return Cursor;\n })();\n\n exports['default'] = Cursor;\n});","define('mobiledoc-kit/utils/cursor/position', ['exports', 'mobiledoc-kit/utils/dom-utils', 'mobiledoc-kit/utils/assert', 'mobiledoc-kit/models/marker', 'mobiledoc-kit/utils/selection-utils', 'mobiledoc-kit/utils/key', 'mobiledoc-kit/utils/cursor/range'], function (exports, _mobiledocKitUtilsDomUtils, _mobiledocKitUtilsAssert, _mobiledocKitModelsMarker, _mobiledocKitUtilsSelectionUtils, _mobiledocKitUtilsKey, _mobiledocKitUtilsCursorRange) {\n 'use strict';\n\n var _get = function get(_x5, _x6, _x7) { var _again = true; _function: while (_again) { var object = _x5, property = _x6, receiver = _x7; _again = false; if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { _x5 = parent; _x6 = property; _x7 = receiver; _again = true; desc = parent = undefined; continue _function; } } else if ('value' in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } } };\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _inherits(subClass, superClass) { if (typeof superClass !== 'function' && superClass !== null) { throw new TypeError('Super expression must either be null or a function, not ' + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n var FORWARD = _mobiledocKitUtilsKey.DIRECTION.FORWARD;\n var BACKWARD = _mobiledocKitUtilsKey.DIRECTION.BACKWARD;\n\n var WORD_CHAR_REGEX = /\\w|_|:/;\n\n function findParentSectionFromNode(renderTree, node) {\n var renderNode = renderTree.findRenderNodeFromElement(node, function (renderNode) {\n return renderNode.postNode.isSection;\n });\n\n return renderNode && renderNode.postNode;\n }\n\n function findOffsetInMarkerable(markerable, node, offset) {\n var offsetInSection = 0;\n var marker = markerable.markers.head;\n while (marker) {\n var markerNode = marker.renderNode.element;\n if (markerNode === node) {\n return offsetInSection + offset;\n } else if (marker.isAtom) {\n if (marker.renderNode.headTextNode === node) {\n return offsetInSection;\n } else if (marker.renderNode.tailTextNode === node) {\n return offsetInSection + 1;\n }\n }\n\n offsetInSection += marker.length;\n marker = marker.next;\n }\n\n return offsetInSection;\n }\n\n function findOffsetInSection(section, node, offset) {\n if (section.isMarkerable) {\n return findOffsetInMarkerable(section, node, offset);\n } else {\n (0, _mobiledocKitUtilsAssert['default'])('findOffsetInSection must be called with markerable or card section', section.isCardSection);\n\n var wrapperNode = section.renderNode.element;\n var endTextNode = wrapperNode.lastChild;\n if (node === endTextNode) {\n return 1;\n }\n return 0;\n }\n }\n\n var Position = undefined,\n BlankPosition = undefined;\n\n Position = (function () {\n /**\n * A position is a logical location (zero-width, or \"collapsed\") in a post,\n * typically between two characters in a section.\n * Two positions (a head and a tail) make up a {@link Range}.\n * @constructor\n */\n\n function Position(section) {\n var offset = arguments.length <= 1 || arguments[1] === undefined ? 0 : arguments[1];\n var isBlank = arguments.length <= 2 || arguments[2] === undefined ? false : arguments[2];\n\n _classCallCheck(this, Position);\n\n if (!isBlank) {\n (0, _mobiledocKitUtilsAssert['default'])('Position must have a section that is addressable by the cursor', section && section.isLeafSection);\n (0, _mobiledocKitUtilsAssert['default'])('Position must have numeric offset', typeof offset === 'number');\n }\n\n this.section = section;\n this.offset = offset;\n this.isBlank = isBlank;\n }\n\n /**\n * @param {integer} x x-position in current viewport\n * @param {integer} y y-position in current viewport\n * @param {Editor} editor\n * @return {Position|null}\n */\n\n _createClass(Position, [{\n key: 'toRange',\n\n /**\n * Returns a range from this position to the given tail. If no explicit\n * tail is given this returns a collapsed range focused on this position.\n * @param {Position} [tail=this] The ending position\n * @return {Range}\n * @public\n */\n value: function toRange() {\n var tail = arguments.length <= 0 || arguments[0] === undefined ? this : arguments[0];\n var direction = arguments.length <= 1 || arguments[1] === undefined ? null : arguments[1];\n\n return new _mobiledocKitUtilsCursorRange['default'](this, tail, direction);\n }\n }, {\n key: 'markerIn',\n\n /**\n * Returns the marker in `direction` from this position.\n * If the position is in the middle of a marker, the direction is irrelevant.\n * Otherwise, if the position is at a boundary between two markers, returns the\n * marker to the left if `direction` === BACKWARD and the marker to the right\n * if `direction` === FORWARD (assuming left-to-right text direction).\n * @param {Direction}\n * @return {Marker|undefined}\n */\n value: function markerIn(direction) {\n if (!this.isMarkerable) {\n return;\n }\n\n var marker = this.marker;\n var offsetInMarker = this.offsetInMarker;\n\n if (!marker) {\n return;\n }\n\n if (offsetInMarker > 0 && offsetInMarker < marker.length) {\n return marker;\n } else if (offsetInMarker === 0) {\n return direction === BACKWARD ? marker : marker.prev;\n } else if (offsetInMarker === marker.length) {\n return direction === FORWARD ? marker.next : marker;\n }\n }\n }, {\n key: 'isEqual',\n value: function isEqual(position) {\n return this.section === position.section && this.offset === position.offset;\n }\n\n /**\n * @return {Boolean} If this position is at the head of the post\n */\n }, {\n key: 'isHeadOfPost',\n value: function isHeadOfPost() {\n return this.move(BACKWARD).isEqual(this);\n }\n\n /**\n * @return {Boolean} If this position is at the tail of the post\n */\n }, {\n key: 'isTailOfPost',\n value: function isTailOfPost() {\n return this.move(FORWARD).isEqual(this);\n }\n\n /**\n * @return {Boolean} If this position is at the head of its section\n */\n }, {\n key: 'isHead',\n value: function isHead() {\n return this.isEqual(this.section.headPosition());\n }\n\n /**\n * @return {Boolean} If this position is at the tail of its section\n */\n }, {\n key: 'isTail',\n value: function isTail() {\n return this.isEqual(this.section.tailPosition());\n }\n\n /**\n * Move the position 1 unit in `direction`.\n *\n * @param {Number} units to move. > 0 moves right, < 0 moves left\n * @return {Position} Return a new position one unit in the given\n * direction. If the position is moving left and at the beginning of the post,\n * the same position will be returned. Same if the position is moving right and\n * at the end of the post.\n */\n }, {\n key: 'move',\n value: function move(units) {\n (0, _mobiledocKitUtilsAssert['default'])('Must pass integer to Position#move', typeof units === 'number');\n\n if (units < 0) {\n return this.moveLeft().move(++units);\n } else if (units > 0) {\n return this.moveRight().move(--units);\n } else {\n return this;\n }\n }\n\n /**\n * @param {Number} direction (FORWARD or BACKWARD)\n * @return {Position} The result of moving 1 \"word\" unit in `direction`\n */\n }, {\n key: 'moveWord',\n value: function moveWord(direction) {\n var isPostBoundary = direction === BACKWARD ? this.isHeadOfPost() : this.isTailOfPost();\n if (isPostBoundary) {\n return this;\n }\n\n if (!this.isMarkerable) {\n return this.move(direction);\n }\n\n var pos = this;\n\n // Helper fn to check if the pos is at the `dir` boundary of its section\n var isBoundary = function isBoundary(pos, dir) {\n return dir === BACKWARD ? pos.isHead() : pos.isTail();\n };\n // Get the char at this position (looking forward/right)\n var getChar = function getChar(pos) {\n var marker = pos.marker;\n var offsetInMarker = pos.offsetInMarker;\n\n return marker.charAt(offsetInMarker);\n };\n // Get the char in `dir` at this position\n var peekChar = function peekChar(pos, dir) {\n return dir === BACKWARD ? getChar(pos.move(BACKWARD)) : getChar(pos);\n };\n // Whether there is an atom in `dir` from this position\n var isAtom = function isAtom(pos, dir) {\n // Special case when position is at end, the marker associated with it is\n // the marker to its left. Normally `pos#marker` is the marker to the right of the pos's offset.\n if (dir === BACKWARD && pos.isTail() && pos.marker.isAtom) {\n return true;\n }\n return dir === BACKWARD ? pos.move(BACKWARD).marker.isAtom : pos.marker.isAtom;\n };\n\n if (isBoundary(pos, direction)) {\n // extend movement into prev/next section\n return pos.move(direction).moveWord(direction);\n }\n\n var seekWord = function seekWord(pos) {\n return !isBoundary(pos, direction) && !isAtom(pos, direction) && !WORD_CHAR_REGEX.test(peekChar(pos, direction));\n };\n\n // move(dir) while we are seeking the first word char\n while (seekWord(pos)) {\n pos = pos.move(direction);\n }\n\n if (isAtom(pos, direction)) {\n return pos.move(direction);\n }\n\n var seekBoundary = function seekBoundary(pos) {\n return !isBoundary(pos, direction) && !isAtom(pos, direction) && WORD_CHAR_REGEX.test(peekChar(pos, direction));\n };\n\n // move(dir) while we are seeking the first boundary position\n while (seekBoundary(pos)) {\n pos = pos.move(direction);\n }\n\n return pos;\n }\n\n /**\n * The position to the left of this position.\n * If this position is the post's headPosition it returns itself.\n * @return {Position}\n * @private\n */\n }, {\n key: 'moveLeft',\n value: function moveLeft() {\n if (this.isHead()) {\n var prev = this.section.previousLeafSection();\n return prev ? prev.tailPosition() : this;\n } else {\n var offset = this.offset - 1;\n if (this.isMarkerable && this.marker) {\n var code = this.marker.value.charCodeAt(offset);\n if (code >= _mobiledocKitModelsMarker.LOW_SURROGATE_RANGE[0] && code <= _mobiledocKitModelsMarker.LOW_SURROGATE_RANGE[1]) {\n offset = offset - 1;\n }\n }\n return new Position(this.section, offset);\n }\n }\n\n /**\n * The position to the right of this position.\n * If this position is the post's tailPosition it returns itself.\n * @return {Position}\n * @private\n */\n }, {\n key: 'moveRight',\n value: function moveRight() {\n if (this.isTail()) {\n var next = this.section.nextLeafSection();\n return next ? next.headPosition() : this;\n } else {\n var offset = this.offset + 1;\n if (this.isMarkerable && this.marker) {\n var code = this.marker.value.charCodeAt(offset - 1);\n if (code >= _mobiledocKitModelsMarker.HIGH_SURROGATE_RANGE[0] && code <= _mobiledocKitModelsMarker.HIGH_SURROGATE_RANGE[1]) {\n offset = offset + 1;\n }\n }\n return new Position(this.section, offset);\n }\n }\n }, {\n key: 'leafSectionIndex',\n get: function get() {\n var _this = this;\n\n var post = this.section.post;\n var leafSectionIndex = undefined;\n post.walkAllLeafSections(function (section, index) {\n if (section === _this.section) {\n leafSectionIndex = index;\n }\n });\n return leafSectionIndex;\n }\n }, {\n key: 'isMarkerable',\n get: function get() {\n return this.section && this.section.isMarkerable;\n }\n\n /**\n * Returns the marker at this position, in the backward direction\n * (i.e., the marker to the left of the cursor if the cursor is on a marker boundary and text is left-to-right)\n * @return {Marker|undefined}\n */\n }, {\n key: 'marker',\n get: function get() {\n return this.isMarkerable && this.markerPosition.marker;\n }\n }, {\n key: 'offsetInMarker',\n get: function get() {\n return this.markerPosition.offset;\n }\n }, {\n key: 'markerPosition',\n\n /**\n * @private\n */\n get: function get() {\n (0, _mobiledocKitUtilsAssert['default'])('Cannot get markerPosition without a section', !!this.section);\n (0, _mobiledocKitUtilsAssert['default'])('cannot get markerPosition of a non-markerable', !!this.section.isMarkerable);\n return this.section.markerPositionAtOffset(this.offset);\n }\n }], [{\n key: 'atPoint',\n value: function atPoint(x, y, editor) {\n var _renderTree = editor._renderTree;\n var rootElement = editor.element;\n\n var elementFromPoint = document.elementFromPoint(x, y);\n if (!(0, _mobiledocKitUtilsDomUtils.containsNode)(rootElement, elementFromPoint)) {\n return;\n }\n\n var _findOffsetInNode = (0, _mobiledocKitUtilsSelectionUtils.findOffsetInNode)(elementFromPoint, { left: x, top: y });\n\n var node = _findOffsetInNode.node;\n var offset = _findOffsetInNode.offset;\n\n return Position.fromNode(_renderTree, node, offset);\n }\n }, {\n key: 'blankPosition',\n value: function blankPosition() {\n return new BlankPosition();\n }\n }, {\n key: 'fromNode',\n value: function fromNode(renderTree, node, offset) {\n if ((0, _mobiledocKitUtilsDomUtils.isTextNode)(node)) {\n return Position.fromTextNode(renderTree, node, offset);\n } else {\n return Position.fromElementNode(renderTree, node, offset);\n }\n }\n }, {\n key: 'fromTextNode',\n value: function fromTextNode(renderTree, textNode, offsetInNode) {\n var renderNode = renderTree.getElementRenderNode(textNode);\n var section = undefined,\n offsetInSection = undefined;\n\n if (renderNode) {\n var marker = renderNode.postNode;\n section = marker.section;\n\n (0, _mobiledocKitUtilsAssert['default'])('Could not find parent section for mapped text node \"' + textNode.textContent + '\"', !!section);\n offsetInSection = section.offsetOfMarker(marker, offsetInNode);\n } else {\n // all text nodes should be rendered by markers except:\n // * text nodes inside cards\n // * text nodes created by the browser during text input\n // both of these should have rendered parent sections, though\n section = findParentSectionFromNode(renderTree, textNode);\n (0, _mobiledocKitUtilsAssert['default'])('Could not find parent section for un-mapped text node \"' + textNode.textContent + '\"', !!section);\n\n offsetInSection = findOffsetInSection(section, textNode, offsetInNode);\n }\n\n return new Position(section, offsetInSection);\n }\n }, {\n key: 'fromElementNode',\n value: function fromElementNode(renderTree, elementNode, offset) {\n var position = undefined;\n\n // The browser may change the reported selection to equal the editor's root\n // element if the user clicks an element that is immediately removed,\n // which can happen when clicking to remove a card.\n if (elementNode === renderTree.rootElement) {\n var post = renderTree.rootNode.postNode;\n position = offset === 0 ? post.headPosition() : post.tailPosition();\n } else {\n var section = findParentSectionFromNode(renderTree, elementNode);\n (0, _mobiledocKitUtilsAssert['default'])('Could not find parent section from element node', !!section);\n\n if (section.isCardSection) {\n // Selections in cards are usually made on a text node\n // containing a ‌ on one side or the other of the card but\n // some scenarios (Firefox) will result in selecting the\n // card's wrapper div. If the offset is 2 we've selected\n // the final zwnj and should consider the cursor at the\n // end of the card (offset 1). Otherwise, the cursor is at\n // the start of the card\n position = offset < 2 ? section.headPosition() : section.tailPosition();\n } else {\n\n // In Firefox it is possible for the cursor to be on an atom's wrapper\n // element. (In Chrome/Safari, the browser corrects this to be on\n // one of the text nodes surrounding the wrapper).\n // This code corrects for when the browser reports the cursor position\n // to be on the wrapper element itself\n var renderNode = renderTree.getElementRenderNode(elementNode);\n var postNode = renderNode && renderNode.postNode;\n if (postNode && postNode.isAtom) {\n var sectionOffset = section.offsetOfMarker(postNode);\n if (offset > 1) {\n // we are on the tail side of the atom\n sectionOffset += postNode.length;\n }\n position = new Position(section, sectionOffset);\n } else {\n // The offset is 0 if the cursor is on a non-atom-wrapper element node\n // (e.g., a
tag in a blank markup section)\n position = section.headPosition();\n }\n }\n }\n\n return position;\n }\n }]);\n\n return Position;\n })();\n\n BlankPosition = (function (_Position) {\n _inherits(BlankPosition, _Position);\n\n function BlankPosition() {\n _classCallCheck(this, BlankPosition);\n\n _get(Object.getPrototypeOf(BlankPosition.prototype), 'constructor', this).call(this, null, 0, true);\n }\n\n _createClass(BlankPosition, [{\n key: 'isEqual',\n value: function isEqual(other) {\n return other && other.isBlank;\n }\n }, {\n key: 'toRange',\n value: function toRange() {\n return _mobiledocKitUtilsCursorRange['default'].blankRange();\n }\n }, {\n key: 'isHeadOfPost',\n value: function isHeadOfPost() {\n return false;\n }\n }, {\n key: 'isTailOfPost',\n value: function isTailOfPost() {\n return false;\n }\n }, {\n key: 'isHead',\n value: function isHead() {\n return false;\n }\n }, {\n key: 'isTail',\n value: function isTail() {\n return false;\n }\n }, {\n key: 'move',\n value: function move() {\n return this;\n }\n }, {\n key: 'moveWord',\n value: function moveWord() {\n return this;\n }\n }, {\n key: 'leafSectionIndex',\n get: function get() {\n (0, _mobiledocKitUtilsAssert['default'])('must implement get leafSectionIndex', false);\n }\n }, {\n key: 'isMarkerable',\n get: function get() {\n return false;\n }\n }, {\n key: 'marker',\n get: function get() {\n return false;\n }\n }, {\n key: 'markerPosition',\n get: function get() {\n return {};\n }\n }]);\n\n return BlankPosition;\n })(Position);\n\n exports['default'] = Position;\n});","define('mobiledoc-kit/utils/cursor/range', ['exports', 'mobiledoc-kit/utils/cursor/position', 'mobiledoc-kit/utils/key', 'mobiledoc-kit/utils/assert'], function (exports, _mobiledocKitUtilsCursorPosition, _mobiledocKitUtilsKey, _mobiledocKitUtilsAssert) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n /**\n * A logical range of a {@link Post}.\n * Usually an instance of Range will be read from the {@link Editor#range} property,\n * but it may be useful to instantiate a range directly when programmatically modifying a Post.\n */\n\n var Range = (function () {\n /**\n * @param {Position} head\n * @param {Position} [tail=head]\n * @param {Direction} [direction=null]\n * @return {Range}\n * @private\n */\n\n function Range(head) {\n var tail = arguments.length <= 1 || arguments[1] === undefined ? head : arguments[1];\n var direction = arguments.length <= 2 || arguments[2] === undefined ? null : arguments[2];\n return (function () {\n _classCallCheck(this, Range);\n\n /** @property {Position} head */\n this.head = head;\n\n /** @property {Position} tail */\n this.tail = tail;\n\n /** @property {Direction} direction */\n this.direction = direction;\n }).apply(this, arguments);\n }\n\n /**\n * Shorthand to create a new range from a section(s) and offset(s).\n * When given only a head section and offset, creates a collapsed range.\n * @param {Section} headSection\n * @param {number} headOffset\n * @param {Section} [tailSection=headSection]\n * @param {number} [tailOffset=headOffset]\n * @param {Direction} [direction=null]\n * @return {Range}\n */\n\n _createClass(Range, [{\n key: 'trimTo',\n\n /**\n * @param {Markerable} section\n * @return {Range} A range that is constrained to only the part that\n * includes the section.\n * FIXME -- if the section isn't the head or tail, it's assumed to be\n * wholly contained. It's possible to call `trimTo` with a selection that is\n * outside of the range, though, which would invalidate that assumption.\n * There's no efficient way to determine if a section is within a range, yet.\n * @private\n */\n value: function trimTo(section) {\n var length = section.length;\n\n var headOffset = section === this.head.section ? Math.min(this.head.offset, length) : 0;\n var tailOffset = section === this.tail.section ? Math.min(this.tail.offset, length) : length;\n\n return Range.create(section, headOffset, section, tailOffset);\n }\n\n /**\n * Expands the range 1 unit in the given direction\n * If the range is expandable in the given direction, always returns a\n * non-collapsed range.\n * @param {Number} units If units is > 0, the range is extended to the right,\n * otherwise range is extended to the left.\n * @return {Range}\n * @public\n */\n }, {\n key: 'extend',\n value: function extend(units) {\n (0, _mobiledocKitUtilsAssert['default'])('Must pass integer to Range#extend', typeof units === 'number');\n\n if (units === 0) {\n return this;\n }\n\n var head = this.head;\n var tail = this.tail;\n var currentDirection = this.direction;\n\n switch (currentDirection) {\n case _mobiledocKitUtilsKey.DIRECTION.FORWARD:\n return new Range(head, tail.move(units), currentDirection);\n case _mobiledocKitUtilsKey.DIRECTION.BACKWARD:\n return new Range(head.move(units), tail, currentDirection);\n default:\n var newDirection = units > 0 ? _mobiledocKitUtilsKey.DIRECTION.FORWARD : _mobiledocKitUtilsKey.DIRECTION.BACKWARD;\n return new Range(head, tail, newDirection).extend(units);\n }\n }\n\n /**\n * Moves this range 1 unit in the given direction.\n * If the range is collapsed, returns a collapsed range shifted by 1 unit,\n * otherwise collapses this range to the position at the `direction` end of the range.\n * Always returns a collapsed range.\n * @param {Direction} direction\n * @return {Range}\n * @public\n */\n }, {\n key: 'move',\n value: function move(direction) {\n (0, _mobiledocKitUtilsAssert['default'])('Must pass DIRECTION.FORWARD (' + _mobiledocKitUtilsKey.DIRECTION.FORWARD + ') or DIRECTION.BACKWARD (' + _mobiledocKitUtilsKey.DIRECTION.BACKWARD + ') to Range#move', direction === _mobiledocKitUtilsKey.DIRECTION.FORWARD || direction === _mobiledocKitUtilsKey.DIRECTION.BACKWARD);\n\n var focusedPosition = this.focusedPosition;\n var isCollapsed = this.isCollapsed;\n\n if (isCollapsed) {\n return new Range(focusedPosition.move(direction));\n } else {\n return this._collapse(direction);\n }\n }\n\n /**\n * expand a range to all markers matching a given check\n *\n * @param {Function} detectMarker\n * @return {Range} The expanded range\n *\n * @public\n */\n }, {\n key: 'expandByMarker',\n value: function expandByMarker(detectMarker) {\n var head = this.head;\n var tail = this.tail;\n var direction = this.direction;\n var headSection = head.section;\n\n if (headSection !== tail.section) {\n throw new Error('#expandByMarker does not work across sections. Perhaps you should confirm the range is collapsed');\n }\n\n var firstNotMatchingDetect = function firstNotMatchingDetect(i) {\n return !detectMarker(i);\n };\n\n var headMarker = head.section.markers.detect(firstNotMatchingDetect, head.marker, true);\n headMarker = headMarker && headMarker.next || head.marker;\n var headPosition = new _mobiledocKitUtilsCursorPosition['default'](headSection, headSection.offsetOfMarker(headMarker));\n\n var tailMarker = tail.section.markers.detect(firstNotMatchingDetect, tail.marker);\n tailMarker = tailMarker && tailMarker.prev || tail.marker;\n var tailPosition = new _mobiledocKitUtilsCursorPosition['default'](tail.section, tail.section.offsetOfMarker(tailMarker) + tailMarker.length);\n\n return headPosition.toRange(tailPosition, direction);\n }\n }, {\n key: '_collapse',\n value: function _collapse(direction) {\n return new Range(direction === _mobiledocKitUtilsKey.DIRECTION.BACKWARD ? this.head : this.tail);\n }\n }, {\n key: 'isEqual',\n value: function isEqual(other) {\n return other && this.head.isEqual(other.head) && this.tail.isEqual(other.tail);\n }\n }, {\n key: 'focusedPosition',\n get: function get() {\n return this.direction === _mobiledocKitUtilsKey.DIRECTION.BACKWARD ? this.head : this.tail;\n }\n }, {\n key: 'isBlank',\n get: function get() {\n return this.head.isBlank && this.tail.isBlank;\n }\n\n // \"legacy\" APIs\n }, {\n key: 'headSection',\n get: function get() {\n return this.head.section;\n }\n }, {\n key: 'tailSection',\n get: function get() {\n return this.tail.section;\n }\n }, {\n key: 'headSectionOffset',\n get: function get() {\n return this.head.offset;\n }\n }, {\n key: 'tailSectionOffset',\n get: function get() {\n return this.tail.offset;\n }\n }, {\n key: 'isCollapsed',\n get: function get() {\n return this.head.isEqual(this.tail);\n }\n }, {\n key: 'headMarker',\n get: function get() {\n return this.head.marker;\n }\n }, {\n key: 'tailMarker',\n get: function get() {\n return this.tail.marker;\n }\n }, {\n key: 'headMarkerOffset',\n get: function get() {\n return this.head.offsetInMarker;\n }\n }, {\n key: 'tailMarkerOffset',\n get: function get() {\n return this.tail.offsetInMarker;\n }\n }], [{\n key: 'create',\n value: function create(headSection, headOffset) {\n var tailSection = arguments.length <= 2 || arguments[2] === undefined ? headSection : arguments[2];\n var tailOffset = arguments.length <= 3 || arguments[3] === undefined ? headOffset : arguments[3];\n var direction = arguments.length <= 4 || arguments[4] === undefined ? null : arguments[4];\n return (function () {\n return new Range(new _mobiledocKitUtilsCursorPosition['default'](headSection, headOffset), new _mobiledocKitUtilsCursorPosition['default'](tailSection, tailOffset), direction);\n })();\n }\n }, {\n key: 'blankRange',\n value: function blankRange() {\n return new Range(_mobiledocKitUtilsCursorPosition['default'].blankPosition(), _mobiledocKitUtilsCursorPosition['default'].blankPosition());\n }\n }]);\n\n return Range;\n })();\n\n exports['default'] = Range;\n});","define(\"mobiledoc-kit/utils/deprecate\", [\"exports\"], function (exports) {\n /**\n * Usage:\n * Without a conditional, always prints deprecate message:\n * `deprecate('This is deprecated')`\n *\n * Conditional deprecation, works similarly to `assert`, prints deprecation if\n * conditional is false:\n * `deprecate('Deprecated only if foo !== bar', foo === bar)`\n */\n \"use strict\";\n\n exports[\"default\"] = deprecate;\n\n function deprecate(message) {\n var conditional = arguments.length <= 1 || arguments[1] === undefined ? false : arguments[1];\n\n if (!conditional) {\n console.log(\"[mobiledoc-kit] [DEPRECATED]: \" + message); // jshint ignore:line\n }\n }\n});","define('mobiledoc-kit/utils/dom-utils', ['exports', 'mobiledoc-kit/utils/array-utils'], function (exports, _mobiledocKitUtilsArrayUtils) {\n 'use strict';\n\n var NODE_TYPES = {\n ELEMENT: 1,\n TEXT: 3,\n COMMENT: 8\n };\n\n exports.NODE_TYPES = NODE_TYPES;\n function isTextNode(node) {\n return node.nodeType === NODE_TYPES.TEXT;\n }\n\n function isCommentNode(node) {\n return node.nodeType === NODE_TYPES.COMMENT;\n }\n\n function isElementNode(node) {\n return node.nodeType === NODE_TYPES.ELEMENT;\n }\n\n // perform a pre-order tree traversal of the dom, calling `callbackFn(node)`\n // for every node for which `conditionFn(node)` is true\n function walkDOM(topNode) {\n var callbackFn = arguments.length <= 1 || arguments[1] === undefined ? function () {} : arguments[1];\n var conditionFn = arguments.length <= 2 || arguments[2] === undefined ? function () {\n return true;\n } : arguments[2];\n\n var currentNode = topNode;\n\n if (conditionFn(currentNode)) {\n callbackFn(currentNode);\n }\n\n currentNode = currentNode.firstChild;\n\n while (currentNode) {\n walkDOM(currentNode, callbackFn, conditionFn);\n currentNode = currentNode.nextSibling;\n }\n }\n\n function walkTextNodes(topNode) {\n var callbackFn = arguments.length <= 1 || arguments[1] === undefined ? function () {} : arguments[1];\n\n var conditionFn = function conditionFn(node) {\n return isTextNode(node);\n };\n walkDOM(topNode, callbackFn, conditionFn);\n }\n\n function clearChildNodes(element) {\n while (element.childNodes.length) {\n element.removeChild(element.childNodes[0]);\n }\n }\n\n /**\n * @return {Boolean} true when the child node is contained or the same as\n * (e.g., inclusive containment) the parent node\n * see https://github.com/webmodules/node-contains/blob/master/index.js\n * Mimics the behavior of `Node.contains`, which is broken in IE 10\n * @private\n */\n function containsNode(parentNode, childNode) {\n if (parentNode === childNode) {\n return true;\n }\n var position = parentNode.compareDocumentPosition(childNode);\n return !!(position & Node.DOCUMENT_POSITION_CONTAINED_BY);\n }\n\n /**\n * converts the element's NamedNodeMap of attrs into\n * an object with key-value pairs\n * @param {DOMNode} element\n * @return {Object} key-value pairs\n * @private\n */\n function getAttributes(element) {\n var result = {};\n if (element.hasAttributes()) {\n (0, _mobiledocKitUtilsArrayUtils.forEach)(element.attributes, function (_ref) {\n var name = _ref.name;\n var value = _ref.value;\n\n result[name] = value;\n });\n }\n return result;\n }\n\n function addClassName(element, className) {\n element.classList.add(className);\n }\n\n function removeClassName(element, className) {\n element.classList.remove(className);\n }\n\n function normalizeTagName(tagName) {\n return tagName.toLowerCase();\n }\n\n function parseHTML(html) {\n var div = document.createElement('div');\n div.innerHTML = html;\n return div;\n }\n\n function serializeHTML(node) {\n var div = document.createElement('div');\n div.appendChild(node);\n return div.innerHTML;\n }\n\n exports.containsNode = containsNode;\n exports.clearChildNodes = clearChildNodes;\n exports.getAttributes = getAttributes;\n exports.walkDOM = walkDOM;\n exports.walkTextNodes = walkTextNodes;\n exports.addClassName = addClassName;\n exports.removeClassName = removeClassName;\n exports.normalizeTagName = normalizeTagName;\n exports.isTextNode = isTextNode;\n exports.isCommentNode = isCommentNode;\n exports.isElementNode = isElementNode;\n exports.parseHTML = parseHTML;\n exports.serializeHTML = serializeHTML;\n});","define('mobiledoc-kit/utils/element-map', ['exports', 'mobiledoc-kit/utils/assert'], function (exports, _mobiledocKitUtilsAssert) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n // start at one to make the falsy semantics easier\n var uuidGenerator = 1;\n\n var ElementMap = (function () {\n function ElementMap() {\n _classCallCheck(this, ElementMap);\n\n this._map = {};\n }\n\n _createClass(ElementMap, [{\n key: 'set',\n value: function set(key, value) {\n var uuid = key._uuid;\n if (!uuid) {\n key._uuid = uuid = '' + uuidGenerator++;\n }\n this._map[uuid] = value;\n }\n }, {\n key: 'get',\n value: function get(key) {\n if (key._uuid) {\n return this._map[key._uuid];\n }\n return null;\n }\n }, {\n key: 'remove',\n value: function remove(key) {\n (0, _mobiledocKitUtilsAssert['default'])('tried to fetch a value for an element not seen before', !!key._uuid);\n delete this._map[key._uuid];\n }\n }]);\n\n return ElementMap;\n })();\n\n exports['default'] = ElementMap;\n});","define('mobiledoc-kit/utils/element-utils', ['exports', 'mobiledoc-kit/utils/string-utils', 'mobiledoc-kit/utils/dom-utils'], function (exports, _mobiledocKitUtilsStringUtils, _mobiledocKitUtilsDomUtils) {\n 'use strict';\n\n function getEventTargetMatchingTag(tagName, target, container) {\n tagName = (0, _mobiledocKitUtilsDomUtils.normalizeTagName)(tagName);\n // Traverses up DOM from an event target to find the node matching specifed tag\n while (target && target !== container) {\n if ((0, _mobiledocKitUtilsDomUtils.normalizeTagName)(target.tagName) === tagName) {\n return target;\n }\n target = target.parentNode;\n }\n }\n\n function getElementRelativeOffset(element) {\n var offset = { left: 0, top: -window.pageYOffset };\n var offsetParent = element.offsetParent;\n var offsetParentPosition = window.getComputedStyle(offsetParent).position;\n var offsetParentRect;\n\n if (offsetParentPosition === 'relative') {\n offsetParentRect = offsetParent.getBoundingClientRect();\n offset.left = offsetParentRect.left;\n offset.top = offsetParentRect.top;\n }\n return offset;\n }\n\n function getElementComputedStyleNumericProp(element, prop) {\n return parseFloat(window.getComputedStyle(element)[prop]);\n }\n\n function positionElementToRect(element, rect, topOffset, leftOffset) {\n var relativeOffset = getElementRelativeOffset(element);\n var style = element.style;\n var round = Math.round;\n var left, top;\n\n topOffset = topOffset || 0;\n leftOffset = leftOffset || 0;\n left = round(rect.left - relativeOffset.left - leftOffset);\n top = round(rect.top - relativeOffset.top - topOffset);\n style.left = left + 'px';\n style.top = top + 'px';\n return { left: left, top: top };\n }\n\n function positionElementHorizontallyCenteredToRect(element, rect, topOffset) {\n var horizontalCenter = element.offsetWidth / 2 - rect.width / 2;\n return positionElementToRect(element, rect, topOffset, horizontalCenter);\n }\n\n function positionElementCenteredBelow(element, belowElement) {\n var elementMargin = getElementComputedStyleNumericProp(element, 'marginTop');\n return positionElementHorizontallyCenteredToRect(element, belowElement.getBoundingClientRect(), -element.offsetHeight - elementMargin);\n }\n\n function setData(element, name, value) {\n if (element.dataset) {\n element.dataset[name] = value;\n } else {\n var dataName = (0, _mobiledocKitUtilsStringUtils.dasherize)(name);\n return element.setAttribute(dataName, value);\n }\n }\n\n exports.setData = setData;\n exports.getEventTargetMatchingTag = getEventTargetMatchingTag;\n exports.getElementRelativeOffset = getElementRelativeOffset;\n exports.getElementComputedStyleNumericProp = getElementComputedStyleNumericProp;\n exports.positionElementToRect = positionElementToRect;\n exports.positionElementHorizontallyCenteredToRect = positionElementHorizontallyCenteredToRect;\n exports.positionElementCenteredBelow = positionElementCenteredBelow;\n});","define('mobiledoc-kit/utils/environment', ['exports'], function (exports) {\n 'use strict';\n\n exports['default'] = {\n hasDOM: function hasDOM() {\n return typeof document !== 'undefined';\n }\n };\n});","define(\"mobiledoc-kit/utils/fixed-queue\", [\"exports\"], function (exports) {\n \"use strict\";\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if (\"value\" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError(\"Cannot call a class as a function\"); } }\n\n var FixedQueue = (function () {\n function FixedQueue() {\n var length = arguments.length <= 0 || arguments[0] === undefined ? 0 : arguments[0];\n\n _classCallCheck(this, FixedQueue);\n\n this._maxLength = length;\n this._items = [];\n }\n\n _createClass(FixedQueue, [{\n key: \"pop\",\n value: function pop() {\n return this._items.pop();\n }\n }, {\n key: \"push\",\n value: function push(item) {\n this._items.push(item);\n if (this.length > this._maxLength) {\n this._items.shift();\n }\n }\n }, {\n key: \"clear\",\n value: function clear() {\n this._items = [];\n }\n }, {\n key: \"toArray\",\n value: function toArray() {\n return this._items;\n }\n }, {\n key: \"length\",\n get: function get() {\n return this._items.length;\n }\n }]);\n\n return FixedQueue;\n })();\n\n exports[\"default\"] = FixedQueue;\n});","define('mobiledoc-kit/utils/key', ['exports', 'mobiledoc-kit/utils/keycodes', 'mobiledoc-kit/utils/characters', 'mobiledoc-kit/utils/assert'], function (exports, _mobiledocKitUtilsKeycodes, _mobiledocKitUtilsCharacters, _mobiledocKitUtilsAssert) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n exports.modifierMask = modifierMask;\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n /**\n * @typedef Direction\n * @enum {number}\n * @property {number} FORWARD\n * @property {number} BACKWARD\n */\n var DIRECTION = {\n FORWARD: 1,\n BACKWARD: -1\n };\n exports.DIRECTION = DIRECTION;\n var MODIFIERS = {\n META: 1, // also called \"command\" on OS X\n CTRL: 2,\n SHIFT: 4,\n ALT: 8 // also called \"option\" on OS X\n };\n\n exports.MODIFIERS = MODIFIERS;\n\n function modifierMask(event) {\n var metaKey = event.metaKey;\n var shiftKey = event.shiftKey;\n var ctrlKey = event.ctrlKey;\n var altKey = event.altKey;\n\n var modVal = function modVal(val, modifier) {\n return val && modifier || 0;\n };\n return modVal(metaKey, MODIFIERS.META) + modVal(shiftKey, MODIFIERS.SHIFT) + modVal(ctrlKey, MODIFIERS.CTRL) + modVal(altKey, MODIFIERS.ALT);\n }\n\n var SPECIAL_KEYS = {\n BACKSPACE: _mobiledocKitUtilsKeycodes['default'].BACKSPACE,\n TAB: _mobiledocKitUtilsKeycodes['default'].TAB,\n ENTER: _mobiledocKitUtilsKeycodes['default'].ENTER,\n ESC: _mobiledocKitUtilsKeycodes['default'].ESC,\n SPACE: _mobiledocKitUtilsKeycodes['default'].SPACE,\n PAGEUP: _mobiledocKitUtilsKeycodes['default'].PAGEUP,\n PAGEDOWN: _mobiledocKitUtilsKeycodes['default'].PAGEDOWN,\n END: _mobiledocKitUtilsKeycodes['default'].END,\n HOME: _mobiledocKitUtilsKeycodes['default'].HOME,\n LEFT: _mobiledocKitUtilsKeycodes['default'].LEFT,\n UP: _mobiledocKitUtilsKeycodes['default'].UP,\n RIGHT: _mobiledocKitUtilsKeycodes['default'].RIGHT,\n DOWN: _mobiledocKitUtilsKeycodes['default'].DOWN,\n INS: _mobiledocKitUtilsKeycodes['default'].INS,\n DEL: _mobiledocKitUtilsKeycodes['default'].DELETE\n };\n\n exports.SPECIAL_KEYS = SPECIAL_KEYS;\n // heuristic for determining if `event` is a key event\n function isKeyEvent(event) {\n return (/^key/.test(event.type)\n );\n }\n\n /**\n * An abstraction around a KeyEvent\n * that key listeners in the editor can use\n * to determine what sort of key was pressed\n */\n var Key = (function () {\n function Key(event) {\n _classCallCheck(this, Key);\n\n this.keyCode = event.keyCode;\n this.charCode = event.charCode;\n this.event = event;\n this.modifierMask = modifierMask(event);\n }\n\n _createClass(Key, [{\n key: 'toString',\n value: function toString() {\n if (this.isTab()) {\n return _mobiledocKitUtilsCharacters.TAB;\n }\n return String.fromCharCode(this.charCode);\n }\n }, {\n key: 'isEscape',\n value: function isEscape() {\n return this.keyCode === _mobiledocKitUtilsKeycodes['default'].ESC;\n }\n }, {\n key: 'isDelete',\n value: function isDelete() {\n return this.keyCode === _mobiledocKitUtilsKeycodes['default'].BACKSPACE || this.keyCode === _mobiledocKitUtilsKeycodes['default'].DELETE;\n }\n }, {\n key: 'isForwardDelete',\n value: function isForwardDelete() {\n return this.keyCode === _mobiledocKitUtilsKeycodes['default'].DELETE;\n }\n }, {\n key: 'isArrow',\n value: function isArrow() {\n return this.isHorizontalArrow() || this.isVerticalArrow();\n }\n }, {\n key: 'isHorizontalArrow',\n value: function isHorizontalArrow() {\n return this.keyCode === _mobiledocKitUtilsKeycodes['default'].LEFT || this.keyCode === _mobiledocKitUtilsKeycodes['default'].RIGHT;\n }\n }, {\n key: 'isHorizontalArrowWithoutModifiersOtherThanShift',\n value: function isHorizontalArrowWithoutModifiersOtherThanShift() {\n return this.isHorizontalArrow() && !(this.ctrlKey || this.metaKey || this.altKey);\n }\n }, {\n key: 'isVerticalArrow',\n value: function isVerticalArrow() {\n return this.keyCode === _mobiledocKitUtilsKeycodes['default'].UP || this.keyCode === _mobiledocKitUtilsKeycodes['default'].DOWN;\n }\n }, {\n key: 'isLeftArrow',\n value: function isLeftArrow() {\n return this.keyCode === _mobiledocKitUtilsKeycodes['default'].LEFT;\n }\n }, {\n key: 'isRightArrow',\n value: function isRightArrow() {\n return this.keyCode === _mobiledocKitUtilsKeycodes['default'].RIGHT;\n }\n }, {\n key: 'isHome',\n value: function isHome() {\n return this.keyCode === _mobiledocKitUtilsKeycodes['default'].HOME;\n }\n }, {\n key: 'isEnd',\n value: function isEnd() {\n return this.keyCode === _mobiledocKitUtilsKeycodes['default'].END;\n }\n }, {\n key: 'isSpace',\n value: function isSpace() {\n return this.keyCode === _mobiledocKitUtilsKeycodes['default'].SPACE;\n }\n }, {\n key: 'isTab',\n value: function isTab() {\n return this.keyCode === _mobiledocKitUtilsKeycodes['default'].TAB;\n }\n }, {\n key: 'isEnter',\n value: function isEnter() {\n return this.keyCode === _mobiledocKitUtilsKeycodes['default'].ENTER;\n }\n\n /**\n * If the shift key is depressed.\n * For example, while holding down meta+shift, pressing the \"v\"\n * key would result in an event whose `Key` had `isShift()` with a truthy value,\n * because the shift key is down when pressing the \"v\".\n * @see {isShiftKey} which checks if the key is actually the shift key itself.\n * @return {bool}\n */\n }, {\n key: 'isShift',\n value: function isShift() {\n return this.shiftKey;\n }\n\n /*\n * If the key is the actual shift key. This is false when the shift key\n * is held down and the source `event` is not the shift key.\n * @see {isShift}\n * @return {bool}\n */\n }, {\n key: 'isShiftKey',\n value: function isShiftKey() {\n return this.keyCode === _mobiledocKitUtilsKeycodes['default'].SHIFT;\n }\n\n /*\n * If the key is the actual alt key (aka \"option\" on mac). This is false when the alt key\n * is held down and the source `event` is not the alt key.\n * @return {bool}\n */\n }, {\n key: 'isAltKey',\n value: function isAltKey() {\n return this.keyCode === _mobiledocKitUtilsKeycodes['default'].ALT;\n }\n\n /*\n * If the key is the actual ctrl key. This is false when the ctrl key\n * is held down and the source `event` is not the ctrl key.\n * @return {bool}\n */\n }, {\n key: 'isCtrlKey',\n value: function isCtrlKey() {\n return this.keyCode === _mobiledocKitUtilsKeycodes['default'].CTRL;\n }\n }, {\n key: 'hasModifier',\n value: function hasModifier(modifier) {\n return modifier & this.modifierMask;\n }\n }, {\n key: 'hasAnyModifier',\n value: function hasAnyModifier() {\n return !!this.modifierMask;\n }\n }, {\n key: 'isPrintable',\n\n /**\n * See https://developer.mozilla.org/en-US/docs/Web/API/KeyboardEvent/keyCode#Printable_keys_in_standard_position\n * and http://stackoverflow.com/a/12467610/137784\n */\n value: function isPrintable() {\n if (this.ctrlKey || this.metaKey) {\n return false;\n }\n\n var code = this.keyCode;\n\n // Firefox calls keypress events for arrow keys, but they should not be\n // considered printable\n if (this.isArrow()) {\n return false;\n }\n\n return code !== 0 || this.toString().length > 0 || code >= _mobiledocKitUtilsKeycodes['default']['0'] && code <= _mobiledocKitUtilsKeycodes['default']['9'] || // number keys\n this.isSpace() || this.isTab() || this.isEnter() || code >= _mobiledocKitUtilsKeycodes['default'].A && code <= _mobiledocKitUtilsKeycodes['default'].Z || // letter keys\n code >= _mobiledocKitUtilsKeycodes['default'].a && code <= _mobiledocKitUtilsKeycodes['default'].z || code >= _mobiledocKitUtilsKeycodes['default'].NUMPAD_0 && code <= _mobiledocKitUtilsKeycodes['default'].NUMPAD_9 || // numpad keys\n code >= _mobiledocKitUtilsKeycodes['default'][';'] && code <= _mobiledocKitUtilsKeycodes['default']['`'] || // punctuation\n code >= _mobiledocKitUtilsKeycodes['default']['['] && code <= _mobiledocKitUtilsKeycodes['default']['\"'] ||\n // FIXME the IME action seems to get lost when we issue an `editor.deleteSelection`\n // before it (in Chrome)\n code === _mobiledocKitUtilsKeycodes['default'].IME;\n }\n }, {\n key: 'direction',\n get: function get() {\n switch (true) {\n case this.isDelete():\n return this.isForwardDelete() ? DIRECTION.FORWARD : DIRECTION.BACKWARD;\n case this.isHorizontalArrow():\n return this.isRightArrow() ? DIRECTION.FORWARD : DIRECTION.BACKWARD;\n }\n }\n }, {\n key: 'ctrlKey',\n get: function get() {\n return MODIFIERS.CTRL & this.modifierMask;\n }\n }, {\n key: 'metaKey',\n get: function get() {\n return MODIFIERS.META & this.modifierMask;\n }\n }, {\n key: 'shiftKey',\n get: function get() {\n return MODIFIERS.SHIFT & this.modifierMask;\n }\n }, {\n key: 'altKey',\n get: function get() {\n return MODIFIERS.ALT & this.modifierMask;\n }\n }], [{\n key: 'fromEvent',\n value: function fromEvent(event) {\n (0, _mobiledocKitUtilsAssert['default'])('Must pass a Key event to Key.fromEvent', event && isKeyEvent(event));\n return new Key(event);\n }\n }]);\n\n return Key;\n })();\n\n exports['default'] = Key;\n});","define('mobiledoc-kit/utils/keycodes', ['exports'], function (exports) {\n 'use strict';\n\n exports['default'] = {\n BACKSPACE: 8,\n SPACE: 32,\n ENTER: 13,\n SHIFT: 16,\n ESC: 27,\n DELETE: 46,\n '0': 48,\n '9': 57,\n A: 65,\n Z: 90,\n a: 97,\n z: 122,\n 'NUMPAD_0': 186,\n 'NUMPAD_9': 111,\n ';': 186,\n '.': 190,\n '`': 192,\n '[': 219,\n '\"': 222,\n\n // Input Method Editor uses multiple keystrokes to display characters.\n // Example on mac: press option-i then i. This fires 2 key events in Chrome\n // with keyCode 229 and displays ˆ and then î.\n // See http://lists.w3.org/Archives/Public/www-dom/2010JulSep/att-0182/keyCode-spec.html#fixed-virtual-key-codes\n IME: 229,\n\n TAB: 9,\n PAGEUP: 33,\n PAGEDOWN: 34,\n END: 35,\n HOME: 36,\n LEFT: 37,\n UP: 38,\n RIGHT: 39,\n DOWN: 40,\n INS: 45,\n META: 91,\n ALT: 18,\n CTRL: 17\n };\n});","define(\"mobiledoc-kit/utils/linked-item\", [\"exports\"], function (exports) {\n \"use strict\";\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError(\"Cannot call a class as a function\"); } }\n\n var LinkedItem = function LinkedItem() {\n _classCallCheck(this, LinkedItem);\n\n this.next = null;\n this.prev = null;\n };\n\n exports[\"default\"] = LinkedItem;\n});","define('mobiledoc-kit/utils/linked-list', ['exports', 'mobiledoc-kit/utils/assert'], function (exports, _mobiledocKitUtilsAssert) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n var PARENT_PROP = '__parent';\n\n var LinkedList = (function () {\n function LinkedList(options) {\n _classCallCheck(this, LinkedList);\n\n this.head = null;\n this.tail = null;\n this.length = 0;\n\n if (options) {\n var adoptItem = options.adoptItem;\n var freeItem = options.freeItem;\n\n this._adoptItem = adoptItem;\n this._freeItem = freeItem;\n }\n }\n\n _createClass(LinkedList, [{\n key: 'adoptItem',\n value: function adoptItem(item) {\n item[PARENT_PROP] = this;\n this.length++;\n if (this._adoptItem) {\n this._adoptItem(item);\n }\n }\n }, {\n key: 'freeItem',\n value: function freeItem(item) {\n item[PARENT_PROP] = null;\n this.length--;\n if (this._freeItem) {\n this._freeItem(item);\n }\n }\n }, {\n key: 'prepend',\n value: function prepend(item) {\n this.insertBefore(item, this.head);\n }\n }, {\n key: 'append',\n value: function append(item) {\n this.insertBefore(item, null);\n }\n }, {\n key: 'insertAfter',\n value: function insertAfter(item, prevItem) {\n var nextItem = prevItem ? prevItem.next : this.head;\n this.insertBefore(item, nextItem);\n }\n }, {\n key: '_ensureItemIsNotAlreadyInList',\n value: function _ensureItemIsNotAlreadyInList(item) {\n (0, _mobiledocKitUtilsAssert['default'])('Cannot insert an item into a list if it is already in a list', !item.next && !item.prev && this.head !== item);\n }\n }, {\n key: 'insertBefore',\n value: function insertBefore(item, nextItem) {\n this._ensureItemIsNotInList(item);\n this.adoptItem(item);\n\n var insertPos = undefined;\n if (nextItem && nextItem.prev) {\n insertPos = 'middle';\n } else if (nextItem) {\n insertPos = 'start';\n } else {\n insertPos = 'end';\n }\n\n switch (insertPos) {\n case 'start':\n if (this.head) {\n item.next = this.head;\n this.head.prev = item;\n }\n this.head = item;\n\n break;\n case 'middle':\n var prevItem = nextItem.prev;\n item.next = nextItem;\n item.prev = prevItem;\n nextItem.prev = item;\n prevItem.next = item;\n\n break;\n case 'end':\n var tail = this.tail;\n item.prev = tail;\n\n if (tail) {\n tail.next = item;\n } else {\n this.head = item;\n }\n this.tail = item;\n\n break;\n }\n }\n }, {\n key: 'remove',\n value: function remove(item) {\n if (!item[PARENT_PROP]) {\n return;\n }\n this._ensureItemIsInThisList(item);\n this.freeItem(item);\n\n var prev = item.prev;\n var next = item.next;\n\n item.prev = null;\n item.next = null;\n\n if (prev) {\n prev.next = next;\n } else {\n this.head = next;\n }\n\n if (next) {\n next.prev = prev;\n } else {\n this.tail = prev;\n }\n }\n }, {\n key: 'forEach',\n value: function forEach(callback) {\n var item = this.head;\n var index = 0;\n while (item) {\n callback(item, index++);\n item = item.next;\n }\n }\n }, {\n key: 'map',\n value: function map(callback) {\n var result = [];\n this.forEach(function (i) {\n return result.push(callback(i));\n });\n return result;\n }\n }, {\n key: 'walk',\n value: function walk(startItem, endItem, callback) {\n var item = startItem || this.head;\n while (item) {\n callback(item);\n if (item === endItem) {\n break;\n }\n item = item.next;\n }\n }\n }, {\n key: 'readRange',\n value: function readRange(startItem, endItem) {\n var items = [];\n this.walk(startItem, endItem, function (item) {\n items.push(item);\n });\n return items;\n }\n }, {\n key: 'toArray',\n value: function toArray() {\n return this.readRange();\n }\n }, {\n key: 'detect',\n value: function detect(callback) {\n var item = arguments.length <= 1 || arguments[1] === undefined ? this.head : arguments[1];\n var reverse = arguments.length <= 2 || arguments[2] === undefined ? false : arguments[2];\n\n while (item) {\n if (callback(item)) {\n return item;\n }\n item = reverse ? item.prev : item.next;\n }\n }\n }, {\n key: 'any',\n value: function any(callback) {\n return !!this.detect(callback);\n }\n }, {\n key: 'every',\n value: function every(callback) {\n var item = this.head;\n while (item) {\n if (!callback(item)) {\n return false;\n }\n item = item.next;\n }\n return true;\n }\n }, {\n key: 'objectAt',\n value: function objectAt(targetIndex) {\n var index = -1;\n return this.detect(function () {\n index++;\n return targetIndex === index;\n });\n }\n }, {\n key: 'splice',\n value: function splice(targetItem, removalCount, newItems) {\n var _this = this;\n\n var item = targetItem;\n var nextItem = item.next;\n var count = 0;\n while (item && count < removalCount) {\n count++;\n nextItem = item.next;\n this.remove(item);\n item = nextItem;\n }\n newItems.forEach(function (newItem) {\n _this.insertBefore(newItem, nextItem);\n });\n }\n }, {\n key: 'removeBy',\n value: function removeBy(conditionFn) {\n var item = this.head;\n while (item) {\n var nextItem = item.next;\n\n if (conditionFn(item)) {\n this.remove(item);\n }\n\n item = nextItem;\n }\n }\n }, {\n key: '_ensureItemIsNotInList',\n value: function _ensureItemIsNotInList(item) {\n (0, _mobiledocKitUtilsAssert['default'])('Cannot insert an item into a list if it is already in a list', !item[PARENT_PROP]);\n }\n }, {\n key: '_ensureItemIsInThisList',\n value: function _ensureItemIsInThisList(item) {\n (0, _mobiledocKitUtilsAssert['default'])('Cannot remove item that is in another list', item[PARENT_PROP] === this);\n }\n }, {\n key: 'isEmpty',\n get: function get() {\n return this.length === 0;\n }\n }]);\n\n return LinkedList;\n })();\n\n exports['default'] = LinkedList;\n});","define(\"mobiledoc-kit/utils/log-manager\", [\"exports\"], function (exports) {\n \"use strict\";\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if (\"value\" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError(\"Cannot call a class as a function\"); } }\n\n var Logger = (function () {\n function Logger(type, manager) {\n _classCallCheck(this, Logger);\n\n this.type = type;\n this.manager = manager;\n }\n\n _createClass(Logger, [{\n key: \"isEnabled\",\n value: function isEnabled() {\n return this.manager.isEnabled(this.type);\n }\n }, {\n key: \"log\",\n value: function log() {\n for (var _len = arguments.length, args = Array(_len), _key = 0; _key < _len; _key++) {\n args[_key] = arguments[_key];\n }\n\n args.unshift(\"[\" + this.type + \"]\");\n if (this.isEnabled()) {\n var _window$console;\n\n (_window$console = window.console).log.apply(_window$console, args);\n }\n }\n }]);\n\n return Logger;\n })();\n\n var LogManager = (function () {\n function LogManager() {\n _classCallCheck(this, LogManager);\n\n this.enabledTypes = [];\n this.allEnabled = false;\n }\n\n _createClass(LogManager, [{\n key: \"for\",\n value: function _for(type) {\n return new Logger(type, this);\n }\n }, {\n key: \"enableAll\",\n value: function enableAll() {\n this.allEnabled = true;\n }\n }, {\n key: \"enableTypes\",\n value: function enableTypes(types) {\n this.enabledTypes = this.enabledTypes.concat(types);\n }\n }, {\n key: \"disable\",\n value: function disable() {\n this.enabledTypes = [];\n this.allEnabled = false;\n }\n }, {\n key: \"isEnabled\",\n value: function isEnabled(type) {\n return this.allEnabled || this.enabledTypes.indexOf(type) !== -1;\n }\n }]);\n\n return LogManager;\n })();\n\n exports[\"default\"] = LogManager;\n});","define('mobiledoc-kit/utils/markuperable', ['exports', 'mobiledoc-kit/utils/dom-utils', 'mobiledoc-kit/utils/array-utils'], function (exports, _mobiledocKitUtilsDomUtils, _mobiledocKitUtilsArrayUtils) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n var Markerupable = (function () {\n function Markerupable() {\n _classCallCheck(this, Markerupable);\n }\n\n _createClass(Markerupable, [{\n key: 'clearMarkups',\n value: function clearMarkups() {\n this.markups = [];\n }\n }, {\n key: 'addMarkup',\n value: function addMarkup(markup) {\n this.markups.push(markup);\n }\n }, {\n key: 'addMarkupAtIndex',\n value: function addMarkupAtIndex(markup, index) {\n this.markups.splice(index, 0, markup);\n }\n }, {\n key: 'removeMarkup',\n value: function removeMarkup(markupOrMarkupCallback) {\n var _this = this;\n\n var callback = undefined;\n if (typeof markupOrMarkupCallback === 'function') {\n callback = markupOrMarkupCallback;\n } else {\n (function () {\n var markup = markupOrMarkupCallback;\n callback = function (_markup) {\n return _markup === markup;\n };\n })();\n }\n\n (0, _mobiledocKitUtilsArrayUtils.forEach)((0, _mobiledocKitUtilsArrayUtils.filter)(this.markups, callback), function (m) {\n return _this._removeMarkup(m);\n });\n }\n }, {\n key: '_removeMarkup',\n value: function _removeMarkup(markup) {\n var index = this.markups.indexOf(markup);\n if (index !== -1) {\n this.markups.splice(index, 1);\n }\n }\n }, {\n key: 'hasMarkup',\n value: function hasMarkup(tagNameOrMarkup) {\n return !!this.getMarkup(tagNameOrMarkup);\n }\n }, {\n key: 'getMarkup',\n value: function getMarkup(tagNameOrMarkup) {\n var _this2 = this;\n\n if (typeof tagNameOrMarkup === 'string') {\n var _ret2 = (function () {\n var tagName = (0, _mobiledocKitUtilsDomUtils.normalizeTagName)(tagNameOrMarkup);\n return {\n v: (0, _mobiledocKitUtilsArrayUtils.detect)(_this2.markups, function (markup) {\n return markup.tagName === tagName;\n })\n };\n })();\n\n if (typeof _ret2 === 'object') return _ret2.v;\n } else {\n var _ret3 = (function () {\n var targetMarkup = tagNameOrMarkup;\n return {\n v: (0, _mobiledocKitUtilsArrayUtils.detect)(_this2.markups, function (markup) {\n return markup === targetMarkup;\n })\n };\n })();\n\n if (typeof _ret3 === 'object') return _ret3.v;\n }\n }\n }, {\n key: 'openedMarkups',\n get: function get() {\n var count = 0;\n if (this.prev) {\n count = (0, _mobiledocKitUtilsArrayUtils.commonItemLength)(this.markups, this.prev.markups);\n }\n\n return this.markups.slice(count);\n }\n }, {\n key: 'closedMarkups',\n get: function get() {\n var count = 0;\n if (this.next) {\n count = (0, _mobiledocKitUtilsArrayUtils.commonItemLength)(this.markups, this.next.markups);\n }\n\n return this.markups.slice(count);\n }\n }]);\n\n return Markerupable;\n })();\n\n exports['default'] = Markerupable;\n});","define(\"mobiledoc-kit/utils/merge\", [\"exports\"], function (exports) {\n \"use strict\";\n\n function mergeWithOptions(original, updates, options) {\n options = options || {};\n for (var prop in updates) {\n if (options.hasOwnProperty(prop)) {\n original[prop] = options[prop];\n } else if (updates.hasOwnProperty(prop)) {\n original[prop] = updates[prop];\n }\n }\n return original;\n }\n\n /**\n * Merges properties of one object into another\n * @private\n */\n function merge(original, updates) {\n return mergeWithOptions(original, updates);\n }\n\n exports.mergeWithOptions = mergeWithOptions;\n exports.merge = merge;\n});","define('mobiledoc-kit/utils/mixin', ['exports'], function (exports) {\n 'use strict';\n\n exports['default'] = mixin;\n var CONSTRUCTOR_FN_NAME = 'constructor';\n\n function mixin(target, source) {\n target = target.prototype;\n // Fallback to just `source` to allow mixing in a plain object (pojo)\n source = source.prototype || source;\n\n Object.getOwnPropertyNames(source).forEach(function (name) {\n if (name !== CONSTRUCTOR_FN_NAME) {\n var descriptor = Object.getOwnPropertyDescriptor(source, name);\n\n Object.defineProperty(target, name, descriptor);\n }\n });\n }\n});","define('mobiledoc-kit/utils/mobiledoc-error', ['exports'], function (exports) {\n 'use strict';\n\n var errorProps = ['description', 'fileName', 'lineNumber', 'message', 'name', 'number', 'stack'];\n\n function MobiledocError() {\n var tmp = Error.apply(this, arguments);\n\n if (Error.captureStackTrace) {\n Error.captureStackTrace(this, this.constructor);\n }\n // Unfortunately errors are not enumerable in Chrome (at least), so `for prop in tmp` doesn't work.\n for (var idx = 0; idx < errorProps.length; idx++) {\n this[errorProps[idx]] = tmp[errorProps[idx]];\n }\n }\n\n MobiledocError.prototype = Object.create(Error.prototype);\n\n exports['default'] = MobiledocError;\n});","define('mobiledoc-kit/utils/parse-utils', ['exports', 'mobiledoc-kit/parsers/mobiledoc', 'mobiledoc-kit/parsers/html', 'mobiledoc-kit/parsers/text'], function (exports, _mobiledocKitParsersMobiledoc, _mobiledocKitParsersHtml, _mobiledocKitParsersText) {\n /* global JSON */\n 'use strict';\n\n exports.getContentFromPasteEvent = getContentFromPasteEvent;\n exports.setClipboardData = setClipboardData;\n exports.parsePostFromPaste = parsePostFromPaste;\n exports.parsePostFromDrop = parsePostFromDrop;\n var MIME_TEXT_PLAIN = 'text/plain';\n exports.MIME_TEXT_PLAIN = MIME_TEXT_PLAIN;\n var MIME_TEXT_HTML = 'text/html';\n exports.MIME_TEXT_HTML = MIME_TEXT_HTML;\n var NONSTANDARD_IE_TEXT_TYPE = 'Text';\n\n exports.NONSTANDARD_IE_TEXT_TYPE = NONSTANDARD_IE_TEXT_TYPE;\n var MOBILEDOC_REGEX = new RegExp(/data\\-mobiledoc='(.*?)'>/);\n\n /**\n * @return {Post}\n * @private\n */\n function parsePostFromHTML(html, builder, plugins) {\n var post = undefined;\n\n if (MOBILEDOC_REGEX.test(html)) {\n var mobiledocString = html.match(MOBILEDOC_REGEX)[1];\n var mobiledoc = JSON.parse(mobiledocString);\n post = _mobiledocKitParsersMobiledoc['default'].parse(builder, mobiledoc);\n } else {\n post = new _mobiledocKitParsersHtml['default'](builder, { plugins: plugins }).parse(html);\n }\n\n return post;\n }\n\n /**\n * @return {Post}\n * @private\n */\n function parsePostFromText(text, builder, plugins) {\n var parser = new _mobiledocKitParsersText['default'](builder, { plugins: plugins });\n var post = parser.parse(text);\n return post;\n }\n\n /**\n * @return {{html: String, text: String}}\n * @private\n */\n\n function getContentFromPasteEvent(event, window) {\n var html = '',\n text = '';\n\n var clipboardData = event.clipboardData;\n\n if (clipboardData && clipboardData.getData) {\n html = clipboardData.getData(MIME_TEXT_HTML);\n text = clipboardData.getData(MIME_TEXT_PLAIN);\n } else if (window.clipboardData && window.clipboardData.getData) {\n // IE\n // The Internet Explorers (including Edge) have a non-standard way of interacting with the\n // Clipboard API (see http://caniuse.com/#feat=clipboard). In short, they expose a global window.clipboardData\n // object instead of the per-event event.clipboardData object on the other browsers.\n html = window.clipboardData.getData(NONSTANDARD_IE_TEXT_TYPE);\n }\n\n return { html: html, text: text };\n }\n\n /**\n * @return {{html: String, text: String}}\n * @private\n */\n function getContentFromDropEvent(event, logger) {\n var html = '',\n text = '';\n\n try {\n html = event.dataTransfer.getData(MIME_TEXT_HTML);\n text = event.dataTransfer.getData(MIME_TEXT_PLAIN);\n } catch (e) {\n // FIXME IE11 does not include any data in the 'text/html' or 'text/plain'\n // mimetypes. It throws an error 'Invalid argument' when attempting to read\n // these properties.\n if (logger) {\n logger.log('Error getting drop data: ', e);\n }\n }\n\n return { html: html, text: text };\n }\n\n /**\n * @param {CopyEvent|CutEvent}\n * @param {Editor}\n * @param {Window}\n * @private\n */\n\n function setClipboardData(event, _ref, window) {\n var mobiledoc = _ref.mobiledoc;\n var html = _ref.html;\n var text = _ref.text;\n\n if (mobiledoc && html) {\n html = '
' + html + '
';\n }\n\n var clipboardData = event.clipboardData;\n var nonstandardClipboardData = window.clipboardData;\n\n if (clipboardData && clipboardData.setData) {\n clipboardData.setData(MIME_TEXT_HTML, html);\n clipboardData.setData(MIME_TEXT_PLAIN, text);\n } else if (nonstandardClipboardData && nonstandardClipboardData.setData) {\n // The Internet Explorers (including Edge) have a non-standard way of interacting with the\n // Clipboard API (see http://caniuse.com/#feat=clipboard). In short, they expose a global window.clipboardData\n // object instead of the per-event event.clipboardData object on the other browsers.\n nonstandardClipboardData.setData(NONSTANDARD_IE_TEXT_TYPE, html);\n }\n }\n\n /**\n * @param {PasteEvent}\n * @param {{builder: Builder, _parserPlugins: Array}} options\n * @return {Post}\n * @private\n */\n\n function parsePostFromPaste(pasteEvent, _ref2) {\n var builder = _ref2.builder;\n var plugins = _ref2._parserPlugins;\n\n var _ref3 = arguments.length <= 2 || arguments[2] === undefined ? { targetFormat: 'html' } : arguments[2];\n\n var targetFormat = _ref3.targetFormat;\n\n var _getContentFromPasteEvent = getContentFromPasteEvent(pasteEvent, window);\n\n var html = _getContentFromPasteEvent.html;\n var text = _getContentFromPasteEvent.text;\n\n if (targetFormat === 'html' && html && html.length) {\n return parsePostFromHTML(html, builder, plugins);\n } else if (text && text.length) {\n return parsePostFromText(text, builder, plugins);\n }\n }\n\n /**\n * @param {DropEvent}\n * @param {Editor} editor\n * @param {Object} [options={}] Can pass a logger\n * @return {Post}\n * @private\n */\n\n function parsePostFromDrop(dropEvent, editor) {\n var _ref4 = arguments.length <= 2 || arguments[2] === undefined ? {} : arguments[2];\n\n var logger = _ref4.logger;\n var builder = editor.builder;\n var plugins = editor._parserPlugins;\n\n var _getContentFromDropEvent = getContentFromDropEvent(dropEvent, logger);\n\n var html = _getContentFromDropEvent.html;\n var text = _getContentFromDropEvent.text;\n\n if (html && html.length) {\n return parsePostFromHTML(html, builder, plugins);\n } else if (text && text.length) {\n return parsePostFromText(text, builder, plugins);\n }\n }\n});","define(\"mobiledoc-kit/utils/placeholder-image-src\", [\"exports\"], function (exports) {\n \"use strict\";\n\n var placeholderImageSrc = \"data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAOEAAADhCAMAAAAJbSJIAAAAMFBMVEXp7vG6vsHm6+63u77Hy868wMPe4+bO09bh5unr8fTR1djAxMfM0NPX3N/c4eTBxcjXRf5TAAACh0lEQVR4nO3b6ZKqMBSFUSQMYZL3f9tbBq/NEEDiqUqOfusn1ZXKbjcQlGQZAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAACC6RkbsGHuabChEtHmiGYfS3EQYM+Sxw/gMQvmcNnYaj6oTDHi73WPn2eqnj9B8zo3TJXcq5uNjXmVff86VwSR3JtryMa1BYqi7S1hJDCVpSigyLcGhJJEwzlCSNtPKrbVhVwsdCfOhH7uuaG3ARV9DwsaOzxt3N1yPqCHhvXytTUz92VDpmE/LLhZwl++R6Sds6sUa/PL6K/2E2fIhw1xdRKefsFolrPc+xNx/N0k/4fpBsdhL2HfeiN+TsDCms8dDpeRyS3P3QDl6Iqaf8L0rTf+80m6Lmn7Ct+4Wxf+/2RY1/YRv3PHz/u+fsCmqgoTnq7Z+8SGviqoh4dnKu1ieqauiakh4/PQ0r6ivqDoSHj0B97eNRVG1JNxV+L4bnxdVecJtRTdFVZ7QU9F1UXUn9FZ0VVRlCav5ob2KLouqKmFjy676u2HsVnRRVFUJq3J+8KCi86IqSthMvyl209Hjijqm3RsqAZ5pNfa5PJ2KelJRjQmr1/r7cfy0ouoSNvOfvbvhvKLaEr4qOin9kTQnrN7LpDZhE/Zmhp6Eq4p+YcKgiipKGFhRRQkDK6ooYfgLbiSMioQkJGF8P5XwHv4O+7AaKiXzaeXh1kMl5AffTUxiKEm/krD94BR8Gdxl1fceSlR58ZhXKbEpyD2amNiBtmrJLTMHL1LF8/rpXkSZXEmz8K8uvAFFNm6Iq0aBLUFOmeCuJ6exrcCmoLpN7kYx891bSAEAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAADgh/wDdr8peyRHLogAAAAASUVORK5CYII=\";\n\n exports[\"default\"] = placeholderImageSrc;\n});","define('mobiledoc-kit/utils/selection-utils', ['exports', 'mobiledoc-kit/utils/key', 'mobiledoc-kit/utils/dom-utils'], function (exports, _mobiledocKitUtilsKey, _mobiledocKitUtilsDomUtils) {\n 'use strict';\n\n function clearSelection() {\n window.getSelection().removeAllRanges();\n }\n\n function textNodeRects(node) {\n var range = document.createRange();\n range.setEnd(node, node.nodeValue.length);\n range.setStart(node, 0);\n return range.getClientRects();\n }\n\n function findOffsetInTextNode(node, coords) {\n var len = node.nodeValue.length;\n var range = document.createRange();\n for (var i = 0; i < len; i++) {\n range.setEnd(node, i + 1);\n range.setStart(node, i);\n var rect = range.getBoundingClientRect();\n if (rect.top === rect.bottom) {\n continue;\n }\n if (rect.left <= coords.left && rect.right >= coords.left && rect.top <= coords.top && rect.bottom >= coords.top) {\n return { node: node, offset: i + (coords.left >= (rect.left + rect.right) / 2 ? 1 : 0) };\n }\n }\n return { node: node, offset: 0 };\n }\n\n /*\n * @param {Object} coords with `top` and `left`\n * @see https://github.com/ProseMirror/prosemirror/blob/4c22e3fe97d87a355a0534e25d65aaf0c0d83e57/src/edit/dompos.js\n * @return {Object} {node, offset}\n */\n function findOffsetInNode(_x, _x2) {\n var _again = true;\n\n _function: while (_again) {\n var node = _x,\n coords = _x2;\n _again = false;\n\n var closest = undefined,\n dyClosest = 1e8,\n coordsClosest = undefined,\n offset = 0;\n for (var child = node.firstChild; child; child = child.nextSibling) {\n var rects = undefined;\n if ((0, _mobiledocKitUtilsDomUtils.isElementNode)(child)) {\n rects = child.getClientRects();\n } else if ((0, _mobiledocKitUtilsDomUtils.isTextNode)(child)) {\n rects = textNodeRects(child);\n } else {\n continue;\n }\n\n for (var i = 0; i < rects.length; i++) {\n var rect = rects[i];\n if (rect.left <= coords.left && rect.right >= coords.left) {\n var dy = rect.top > coords.top ? rect.top - coords.top : rect.bottom < coords.top ? coords.top - rect.bottom : 0;\n if (dy < dyClosest) {\n closest = child;\n dyClosest = dy;\n coordsClosest = dy ? { left: coords.left, top: rect.top } : coords;\n if ((0, _mobiledocKitUtilsDomUtils.isElementNode)(child) && !child.firstChild) {\n offset = i + (coords.left >= (rect.left + rect.right) / 2 ? 1 : 0);\n }\n continue;\n }\n }\n if (!closest && (coords.top >= rect.bottom || coords.top >= rect.top && coords.left >= rect.right)) {\n offset = i + 1;\n }\n }\n }\n if (!closest) {\n return { node: node, offset: offset };\n }\n if ((0, _mobiledocKitUtilsDomUtils.isTextNode)(closest)) {\n return findOffsetInTextNode(closest, coordsClosest);\n }\n if (closest.firstChild) {\n _x = closest;\n _x2 = coordsClosest;\n _again = true;\n closest = dyClosest = coordsClosest = offset = child = rects = i = rect = dy = undefined;\n continue _function;\n }\n return { node: node, offset: offset };\n }\n }\n\n function constrainNodeTo(node, parentNode, existingOffset) {\n var compare = parentNode.compareDocumentPosition(node);\n if (compare & Node.DOCUMENT_POSITION_CONTAINED_BY) {\n // the node is inside parentNode, do nothing\n return { node: node, offset: existingOffset };\n } else if (compare & Node.DOCUMENT_POSITION_CONTAINS) {\n // the node contains parentNode. This shouldn't happen.\n return { node: node, offset: existingOffset };\n } else if (compare & Node.DOCUMENT_POSITION_PRECEDING) {\n // node is before parentNode. return start of deepest first child\n var child = parentNode.firstChild;\n while (child.firstChild) {\n child = child.firstChild;\n }\n return { node: child, offset: 0 };\n } else if (compare & Node.DOCUMENT_POSITION_FOLLOWING) {\n // node is after parentNode. return end of deepest last child\n var child = parentNode.lastChild;\n while (child.lastChild) {\n child = child.lastChild;\n }\n\n var offset = (0, _mobiledocKitUtilsDomUtils.isTextNode)(child) ? child.textContent.length : 1;\n return { node: child, offset: offset };\n } else {\n return { node: node, offset: existingOffset };\n }\n }\n\n /*\n * Returns a new selection that is constrained within parentNode.\n * If the anchorNode or focusNode are outside the parentNode, they are replaced with the beginning\n * or end of the parentNode's children\n */\n function constrainSelectionTo(selection, parentNode) {\n var _constrainNodeTo = constrainNodeTo(selection.anchorNode, parentNode, selection.anchorOffset);\n\n var anchorNode = _constrainNodeTo.node;\n var anchorOffset = _constrainNodeTo.offset;\n\n var _constrainNodeTo2 = constrainNodeTo(selection.focusNode, parentNode, selection.focusOffset);\n\n var focusNode = _constrainNodeTo2.node;\n var focusOffset = _constrainNodeTo2.offset;\n\n return { anchorNode: anchorNode, anchorOffset: anchorOffset, focusNode: focusNode, focusOffset: focusOffset };\n }\n\n function comparePosition(_x3) {\n var _again2 = true;\n\n _function2: while (_again2) {\n var selection = _x3;\n _again2 = false;\n var anchorNode = selection.anchorNode;\n var focusNode = selection.focusNode;\n var anchorOffset = selection.anchorOffset;\n var focusOffset = selection.focusOffset;\n\n var headNode = undefined,\n tailNode = undefined,\n headOffset = undefined,\n tailOffset = undefined,\n direction = undefined;\n\n var position = anchorNode.compareDocumentPosition(focusNode);\n\n // IE may select return focus and anchor nodes far up the DOM tree instead of\n // picking the deepest, most specific possible node. For example in\n //\n //
abcdef
\n //\n // with a cursor between c and d, IE might say the focusNode is
with\n // an offset of 1. However the anchorNode for a selection might still be\n // 2 if there was a selection.\n //\n // This code walks down the DOM tree until a good comparison of position can be\n // made.\n //\n if (position & Node.DOCUMENT_POSITION_CONTAINS) {\n if (focusOffset < focusNode.childNodes.length) {\n focusNode = focusNode.childNodes[focusOffset];\n focusOffset = 0;\n } else {\n // This situation happens on IE when triple-clicking to select.\n // Set the focus to the very last character inside the node.\n while (focusNode.lastChild) {\n focusNode = focusNode.lastChild;\n }\n focusOffset = focusNode.textContent.length;\n }\n\n _x3 = {\n focusNode: focusNode,\n focusOffset: focusOffset,\n anchorNode: anchorNode, anchorOffset: anchorOffset\n };\n _again2 = true;\n anchorNode = focusNode = anchorOffset = focusOffset = headNode = tailNode = headOffset = tailOffset = direction = position = undefined;\n continue _function2;\n } else if (position & Node.DOCUMENT_POSITION_CONTAINED_BY) {\n var offset = anchorOffset - 1;\n if (offset < 0) {\n offset = 0;\n }\n _x3 = {\n anchorNode: anchorNode.childNodes[offset],\n anchorOffset: 0,\n focusNode: focusNode, focusOffset: focusOffset\n };\n _again2 = true;\n anchorNode = focusNode = anchorOffset = focusOffset = headNode = tailNode = headOffset = tailOffset = direction = position = offset = undefined;\n continue _function2;\n\n // The meat of translating anchor and focus nodes to head and tail nodes\n } else if (position & Node.DOCUMENT_POSITION_FOLLOWING) {\n headNode = anchorNode;tailNode = focusNode;\n headOffset = anchorOffset;tailOffset = focusOffset;\n direction = _mobiledocKitUtilsKey.DIRECTION.FORWARD;\n } else if (position & Node.DOCUMENT_POSITION_PRECEDING) {\n headNode = focusNode;tailNode = anchorNode;\n headOffset = focusOffset;tailOffset = anchorOffset;\n direction = _mobiledocKitUtilsKey.DIRECTION.BACKWARD;\n } else {\n // same node\n headNode = tailNode = anchorNode;\n headOffset = anchorOffset;\n tailOffset = focusOffset;\n if (tailOffset < headOffset) {\n // Swap the offset order\n headOffset = focusOffset;\n tailOffset = anchorOffset;\n direction = _mobiledocKitUtilsKey.DIRECTION.BACKWARD;\n } else if (headOffset < tailOffset) {\n direction = _mobiledocKitUtilsKey.DIRECTION.FORWARD;\n } else {\n direction = null;\n }\n }\n\n return { headNode: headNode, headOffset: headOffset, tailNode: tailNode, tailOffset: tailOffset, direction: direction };\n }\n }\n\n exports.clearSelection = clearSelection;\n exports.comparePosition = comparePosition;\n exports.findOffsetInNode = findOffsetInNode;\n exports.constrainSelectionTo = constrainSelectionTo;\n});","define(\"mobiledoc-kit/utils/set\", [\"exports\"], function (exports) {\n \"use strict\";\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if (\"value\" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError(\"Cannot call a class as a function\"); } }\n\n var Set = (function () {\n function Set() {\n var _this = this;\n\n var items = arguments.length <= 0 || arguments[0] === undefined ? [] : arguments[0];\n\n _classCallCheck(this, Set);\n\n this.items = [];\n items.forEach(function (i) {\n return _this.add(i);\n });\n }\n\n _createClass(Set, [{\n key: \"add\",\n value: function add(item) {\n if (!this.has(item)) {\n this.items.push(item);\n }\n }\n }, {\n key: \"has\",\n value: function has(item) {\n return this.items.indexOf(item) !== -1;\n }\n }, {\n key: \"toArray\",\n value: function toArray() {\n return this.items;\n }\n }, {\n key: \"length\",\n get: function get() {\n return this.items.length;\n }\n }]);\n\n return Set;\n })();\n\n exports[\"default\"] = Set;\n});","define('mobiledoc-kit/utils/string-utils', ['exports'], function (exports) {\n /*\n * @param {String} string\n * @return {String} a dasherized string. 'modelIndex' -> 'model-index', etc\n */\n 'use strict';\n\n exports.dasherize = dasherize;\n exports.capitalize = capitalize;\n exports.startsWith = startsWith;\n exports.endsWith = endsWith;\n\n function dasherize(string) {\n return string.replace(/[A-Z]/g, function (match, offset) {\n var lower = match.toLowerCase();\n\n return offset === 0 ? lower : '-' + lower;\n });\n }\n\n function capitalize(string) {\n return string.charAt(0).toUpperCase() + string.slice(1);\n }\n\n function startsWith(string, character) {\n return string.charAt(0) === character;\n }\n\n function endsWith(string, endString) {\n var index = string.lastIndexOf(endString);\n return index !== -1 && index === string.length - endString.length;\n }\n});","define('mobiledoc-kit/utils/to-range', ['exports', 'mobiledoc-kit/utils/cursor/range', 'mobiledoc-kit/utils/cursor/position', 'mobiledoc-kit/utils/assert'], function (exports, _mobiledocKitUtilsCursorRange, _mobiledocKitUtilsCursorPosition, _mobiledocKitUtilsAssert) {\n 'use strict';\n\n exports['default'] = toRange;\n\n function toRange(rangeLike) {\n (0, _mobiledocKitUtilsAssert['default'])('Must pass non-blank object to \"toRange\"', !!rangeLike);\n\n if (rangeLike instanceof _mobiledocKitUtilsCursorRange['default']) {\n return rangeLike;\n } else if (rangeLike instanceof _mobiledocKitUtilsCursorPosition['default']) {\n return rangeLike.toRange();\n }\n\n (0, _mobiledocKitUtilsAssert['default'])('Incorrect structure for rangeLike: ' + rangeLike, false);\n }\n});","define('mobiledoc-kit/version', ['exports'], function (exports) {\n 'use strict';\n\n exports['default'] = '##VERSION##';\n});","define('mobiledoc-kit/views/tooltip', ['exports', 'mobiledoc-kit/views/view', 'mobiledoc-kit/utils/element-utils'], function (exports, _mobiledocKitViewsView, _mobiledocKitUtilsElementUtils) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n var _get = function get(_x, _x2, _x3) { var _again = true; _function: while (_again) { var object = _x, property = _x2, receiver = _x3; _again = false; if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { _x = parent; _x2 = property; _x3 = receiver; _again = true; desc = parent = undefined; continue _function; } } else if ('value' in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } } };\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n function _inherits(subClass, superClass) { if (typeof superClass !== 'function' && superClass !== null) { throw new TypeError('Super expression must either be null or a function, not ' + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }\n\n var DELAY = 200;\n\n var Tooltip = (function (_View) {\n _inherits(Tooltip, _View);\n\n function Tooltip(options) {\n var _this = this;\n\n _classCallCheck(this, Tooltip);\n\n var rootElement = options.rootElement;\n\n var timeout = undefined;\n options.classNames = ['__mobiledoc-tooltip'];\n _get(Object.getPrototypeOf(Tooltip.prototype), 'constructor', this).call(this, options);\n\n this.addEventListener(rootElement, 'mouseover', function (e) {\n var target = (0, _mobiledocKitUtilsElementUtils.getEventTargetMatchingTag)(options.showForTag, e.target, rootElement);\n if (target && target.isContentEditable) {\n timeout = setTimeout(function () {\n _this.showLink(target.href, target);\n }, DELAY);\n }\n });\n\n this.addEventListener(rootElement, 'mouseout', function (e) {\n clearTimeout(timeout);\n var toElement = e.toElement || e.relatedTarget;\n if (toElement && toElement.className !== _this.element.className) {\n _this.hide();\n }\n });\n }\n\n _createClass(Tooltip, [{\n key: 'showMessage',\n value: function showMessage(message, element) {\n var tooltipElement = this.element;\n tooltipElement.innerHTML = message;\n this.show();\n (0, _mobiledocKitUtilsElementUtils.positionElementCenteredBelow)(tooltipElement, element);\n }\n }, {\n key: 'showLink',\n value: function showLink(link, element) {\n var message = '' + link + '';\n this.showMessage(message, element);\n }\n }]);\n\n return Tooltip;\n })(_mobiledocKitViewsView['default']);\n\n exports['default'] = Tooltip;\n});","define('mobiledoc-kit/views/view', ['exports', 'mobiledoc-kit/utils/dom-utils'], function (exports, _mobiledocKitUtilsDomUtils) {\n 'use strict';\n\n var _slicedToArray = (function () { function sliceIterator(arr, i) { var _arr = []; var _n = true; var _d = false; var _e = undefined; try { for (var _i = arr[Symbol.iterator](), _s; !(_n = (_s = _i.next()).done); _n = true) { _arr.push(_s.value); if (i && _arr.length === i) break; } } catch (err) { _d = true; _e = err; } finally { try { if (!_n && _i['return']) _i['return'](); } finally { if (_d) throw _e; } } return _arr; } return function (arr, i) { if (Array.isArray(arr)) { return arr; } else if (Symbol.iterator in Object(arr)) { return sliceIterator(arr, i); } else { throw new TypeError('Invalid attempt to destructure non-iterable instance'); } }; })();\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n var View = (function () {\n function View() {\n var _this = this;\n\n var options = arguments.length <= 0 || arguments[0] === undefined ? {} : arguments[0];\n\n _classCallCheck(this, View);\n\n options.tagName = options.tagName || 'div';\n options.container = options.container || document.body;\n\n this.element = document.createElement(options.tagName);\n this.container = options.container;\n this.isShowing = false;\n\n var classNames = options.classNames || [];\n classNames.forEach(function (name) {\n return (0, _mobiledocKitUtilsDomUtils.addClassName)(_this.element, name);\n });\n this._eventListeners = [];\n }\n\n _createClass(View, [{\n key: 'addEventListener',\n value: function addEventListener(element, type, listener) {\n element.addEventListener(type, listener);\n this._eventListeners.push([element, type, listener]);\n }\n }, {\n key: 'removeAllEventListeners',\n value: function removeAllEventListeners() {\n this._eventListeners.forEach(function (_ref) {\n var _ref2 = _slicedToArray(_ref, 3);\n\n var element = _ref2[0];\n var type = _ref2[1];\n var listener = _ref2[2];\n\n element.removeEventListener(type, listener);\n });\n }\n }, {\n key: 'show',\n value: function show() {\n if (!this.isShowing) {\n this.container.appendChild(this.element);\n this.isShowing = true;\n return true;\n }\n }\n }, {\n key: 'hide',\n value: function hide() {\n if (this.isShowing) {\n this.container.removeChild(this.element);\n this.isShowing = false;\n return true;\n }\n }\n }, {\n key: 'destroy',\n value: function destroy() {\n this.removeAllEventListeners();\n this.hide();\n this.isDestroyed = true;\n }\n }]);\n\n return View;\n })();\n\n exports['default'] = View;\n});","define('mobiledoc-text-renderer/cards/image', ['exports'], function (exports) {\n 'use strict';\n\n exports['default'] = {\n name: 'image-card',\n type: 'text',\n render: function render() {}\n };\n});","define('mobiledoc-text-renderer', ['exports', 'mobiledoc-text-renderer/renderer-factory', 'mobiledoc-text-renderer/utils/render-type'], function (exports, _mobiledocTextRendererRendererFactory, _mobiledocTextRendererUtilsRenderType) {\n 'use strict';\n\n exports.registerGlobal = registerGlobal;\n\n function registerGlobal(window) {\n window.MobiledocTextRenderer = _mobiledocTextRendererRendererFactory['default'];\n }\n\n exports.RENDER_TYPE = _mobiledocTextRendererUtilsRenderType['default'];\n exports['default'] = _mobiledocTextRendererRendererFactory['default'];\n});","define('mobiledoc-text-renderer/renderer-factory', ['exports', 'mobiledoc-text-renderer/renderers/0-2', 'mobiledoc-text-renderer/renderers/0-3', 'mobiledoc-text-renderer/utils/render-type'], function (exports, _mobiledocTextRendererRenderers02, _mobiledocTextRendererRenderers03, _mobiledocTextRendererUtilsRenderType) {\n 'use strict';\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n /**\n * runtime Text renderer\n * renders a mobiledoc to Text\n *\n * input: mobiledoc\n * output: Text (string)\n */\n\n function validateCards(cards) {\n if (!Array.isArray(cards)) {\n throw new Error('`cards` must be passed as an array');\n }\n for (var i = 0; i < cards.length; i++) {\n var card = cards[i];\n if (card.type !== _mobiledocTextRendererUtilsRenderType['default']) {\n throw new Error('Card \"' + card.name + '\" must be type \"' + _mobiledocTextRendererUtilsRenderType['default'] + '\", was \"' + card.type + '\"');\n }\n if (!card.render) {\n throw new Error('Card \"' + card.name + '\" must define `render`');\n }\n }\n }\n\n function validateAtoms(atoms) {\n if (!Array.isArray(atoms)) {\n throw new Error('`atoms` must be passed as an array');\n }\n for (var i = 0; i < atoms.length; i++) {\n var atom = atoms[i];\n if (atom.type !== _mobiledocTextRendererUtilsRenderType['default']) {\n throw new Error('Atom \"' + atom.name + '\" must be type \"' + _mobiledocTextRendererUtilsRenderType['default'] + '\", was \"' + atom.type + '\"');\n }\n if (!atom.render) {\n throw new Error('Atom \"' + atom.name + '\" must define `render`');\n }\n }\n }\n\n var RendererFactory = (function () {\n function RendererFactory() {\n var _ref = arguments.length <= 0 || arguments[0] === undefined ? {} : arguments[0];\n\n var cards = _ref.cards;\n var atoms = _ref.atoms;\n var cardOptions = _ref.cardOptions;\n var unknownCardHandler = _ref.unknownCardHandler;\n var unknownAtomHandler = _ref.unknownAtomHandler;\n\n _classCallCheck(this, RendererFactory);\n\n cards = cards || [];\n validateCards(cards);\n atoms = atoms || [];\n validateAtoms(atoms);\n cardOptions = cardOptions || {};\n\n this.state = { cards: cards, atoms: atoms, cardOptions: cardOptions, unknownCardHandler: unknownCardHandler, unknownAtomHandler: unknownAtomHandler };\n }\n\n _createClass(RendererFactory, [{\n key: 'render',\n value: function render(mobiledoc) {\n var version = mobiledoc.version;\n\n switch (version) {\n case _mobiledocTextRendererRenderers02.MOBILEDOC_VERSION:\n return new _mobiledocTextRendererRenderers02['default'](mobiledoc, this.state).render();\n case undefined:\n case null:\n case _mobiledocTextRendererRenderers03.MOBILEDOC_VERSION_0_3:\n case _mobiledocTextRendererRenderers03.MOBILEDOC_VERSION_0_3_1:\n return new _mobiledocTextRendererRenderers03['default'](mobiledoc, this.state).render();\n default:\n throw new Error('Unexpected Mobiledoc version \"' + version + '\"');\n }\n }\n }]);\n\n return RendererFactory;\n })();\n\n exports['default'] = RendererFactory;\n});","define('mobiledoc-text-renderer/renderers/0-2', ['exports', 'mobiledoc-text-renderer/cards/image', 'mobiledoc-text-renderer/utils/render-type', 'mobiledoc-text-renderer/utils/section-types'], function (exports, _mobiledocTextRendererCardsImage, _mobiledocTextRendererUtilsRenderType, _mobiledocTextRendererUtilsSectionTypes) {\n /**\n * runtime Text renderer\n * renders a mobiledoc to Text\n *\n * input: mobiledoc\n * output: Text (string)\n */\n 'use strict';\n\n var _slicedToArray = (function () { function sliceIterator(arr, i) { var _arr = []; var _n = true; var _d = false; var _e = undefined; try { for (var _i = arr[Symbol.iterator](), _s; !(_n = (_s = _i.next()).done); _n = true) { _arr.push(_s.value); if (i && _arr.length === i) break; } } catch (err) { _d = true; _e = err; } finally { try { if (!_n && _i['return']) _i['return'](); } finally { if (_d) throw _e; } } return _arr; } return function (arr, i) { if (Array.isArray(arr)) { return arr; } else if (Symbol.iterator in Object(arr)) { return sliceIterator(arr, i); } else { throw new TypeError('Invalid attempt to destructure non-iterable instance'); } }; })();\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n var LINE_BREAK = '\\n';\n\n var MOBILEDOC_VERSION = '0.2.0';\n\n exports.MOBILEDOC_VERSION = MOBILEDOC_VERSION;\n function validateVersion(version) {\n if (version !== MOBILEDOC_VERSION) {\n throw new Error('Unexpected Mobiledoc version \"' + version + '\"');\n }\n }\n\n var Renderer = (function () {\n function Renderer(mobiledoc, state) {\n _classCallCheck(this, Renderer);\n\n var cards = state.cards;\n var cardOptions = state.cardOptions;\n var atoms = state.atoms;\n var unknownCardHandler = state.unknownCardHandler;\n var version = mobiledoc.version;\n var sectionData = mobiledoc.sections;\n\n validateVersion(version);\n\n var _sectionData = _slicedToArray(sectionData, 2);\n\n var sections = _sectionData[1];\n\n this.root = [];\n this.sections = sections;\n this.cards = cards;\n this.atoms = atoms;\n this.cardOptions = cardOptions;\n this.unknownCardHandler = unknownCardHandler || this._defaultUnknownCardHandler;\n\n this._teardownCallbacks = [];\n }\n\n _createClass(Renderer, [{\n key: 'render',\n value: function render() {\n var _this = this;\n\n this.sections.forEach(function (section) {\n _this.root.push(_this.renderSection(section));\n });\n\n var result = this.root.join(LINE_BREAK);\n return { result: result, teardown: function teardown() {\n return _this.teardown();\n } };\n }\n }, {\n key: 'teardown',\n value: function teardown() {\n for (var i = 0; i < this._teardownCallbacks.length; i++) {\n this._teardownCallbacks[i]();\n }\n }\n }, {\n key: 'renderSection',\n\n // for the text renderer, a missing card is a no-op\n value: function renderSection(section) {\n var _section = _slicedToArray(section, 1);\n\n var type = _section[0];\n\n switch (type) {\n case _mobiledocTextRendererUtilsSectionTypes.MARKUP_SECTION_TYPE:\n return this.renderMarkupSection(section);\n case _mobiledocTextRendererUtilsSectionTypes.IMAGE_SECTION_TYPE:\n return this.renderImageSection(section);\n case _mobiledocTextRendererUtilsSectionTypes.LIST_SECTION_TYPE:\n return this.renderListSection(section);\n case _mobiledocTextRendererUtilsSectionTypes.CARD_SECTION_TYPE:\n return this.renderCardSection(section);\n default:\n throw new Error('Unimplemented renderer for type ' + type);\n }\n }\n }, {\n key: 'renderImageSection',\n value: function renderImageSection() {\n return '';\n }\n }, {\n key: 'renderListSection',\n value: function renderListSection(_ref) {\n var _this2 = this;\n\n var _ref2 = _slicedToArray(_ref, 3);\n\n var type = _ref2[0];\n var tagName = _ref2[1];\n var items = _ref2[2];\n\n return items.map(function (li) {\n return _this2.renderListItem(li);\n }).join(LINE_BREAK);\n }\n }, {\n key: 'renderListItem',\n value: function renderListItem(markers) {\n return this.renderMarkers(markers);\n }\n }, {\n key: 'findCard',\n value: function findCard(name) {\n for (var i = 0; i < this.cards.length; i++) {\n if (this.cards[i].name === name) {\n return this.cards[i];\n }\n }\n if (name === _mobiledocTextRendererCardsImage['default'].name) {\n return _mobiledocTextRendererCardsImage['default'];\n }\n return this._createUnknownCard(name);\n }\n }, {\n key: '_createUnknownCard',\n value: function _createUnknownCard(name) {\n return {\n name: name,\n type: _mobiledocTextRendererUtilsRenderType['default'],\n render: this.unknownCardHandler\n };\n }\n }, {\n key: 'renderCardSection',\n value: function renderCardSection(_ref3) {\n var _ref32 = _slicedToArray(_ref3, 3);\n\n var type = _ref32[0];\n var name = _ref32[1];\n var payload = _ref32[2];\n\n var card = this.findCard(name);\n\n var cardArg = this._createCardArgument(card, payload);\n var rendered = card.render(cardArg);\n\n this._validateCardRender(rendered, card.name);\n\n return rendered || '';\n }\n }, {\n key: '_validateCardRender',\n value: function _validateCardRender(rendered, cardName) {\n if (!rendered) {\n return;\n }\n\n if (typeof rendered !== 'string') {\n throw new Error('Card \"' + cardName + '\" must render ' + _mobiledocTextRendererUtilsRenderType['default'] + ', but result was ' + typeof rendered + '\"');\n }\n }\n }, {\n key: '_registerTeardownCallback',\n value: function _registerTeardownCallback(callback) {\n this._teardownCallbacks.push(callback);\n }\n }, {\n key: '_createCardArgument',\n value: function _createCardArgument(card) {\n var _this3 = this;\n\n var payload = arguments.length <= 1 || arguments[1] === undefined ? {} : arguments[1];\n\n var env = {\n name: card.name,\n isInEditor: false,\n onTeardown: function onTeardown(callback) {\n return _this3._registerTeardownCallback(callback);\n }\n };\n\n var options = this.cardOptions;\n\n return { env: env, options: options, payload: payload };\n }\n }, {\n key: 'renderMarkupSection',\n value: function renderMarkupSection(_ref4) {\n var _ref42 = _slicedToArray(_ref4, 3);\n\n var type = _ref42[0];\n var tagName = _ref42[1];\n var markers = _ref42[2];\n\n return this.renderMarkers(markers);\n }\n }, {\n key: 'renderMarkers',\n value: function renderMarkers(markers) {\n var str = '';\n markers.forEach(function (m) {\n var _m = _slicedToArray(m, 3);\n\n var text = _m[2];\n\n str += text;\n });\n return str;\n }\n }, {\n key: '_defaultUnknownCardHandler',\n get: function get() {\n return function () {};\n }\n }]);\n\n return Renderer;\n })();\n\n exports['default'] = Renderer;\n});","define('mobiledoc-text-renderer/renderers/0-3', ['exports', 'mobiledoc-text-renderer/cards/image', 'mobiledoc-text-renderer/utils/render-type', 'mobiledoc-text-renderer/utils/section-types', 'mobiledoc-text-renderer/utils/marker-types'], function (exports, _mobiledocTextRendererCardsImage, _mobiledocTextRendererUtilsRenderType, _mobiledocTextRendererUtilsSectionTypes, _mobiledocTextRendererUtilsMarkerTypes) {\n /**\n * runtime Text renderer\n * renders a mobiledoc to Text\n *\n * input: mobiledoc\n * output: Text (string)\n */\n 'use strict';\n\n var _slicedToArray = (function () { function sliceIterator(arr, i) { var _arr = []; var _n = true; var _d = false; var _e = undefined; try { for (var _i = arr[Symbol.iterator](), _s; !(_n = (_s = _i.next()).done); _n = true) { _arr.push(_s.value); if (i && _arr.length === i) break; } } catch (err) { _d = true; _e = err; } finally { try { if (!_n && _i['return']) _i['return'](); } finally { if (_d) throw _e; } } return _arr; } return function (arr, i) { if (Array.isArray(arr)) { return arr; } else if (Symbol.iterator in Object(arr)) { return sliceIterator(arr, i); } else { throw new TypeError('Invalid attempt to destructure non-iterable instance'); } }; })();\n\n var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })();\n\n function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } }\n\n var LINE_BREAK = '\\n';\n\n var MOBILEDOC_VERSION_0_3 = '0.3.0';\n exports.MOBILEDOC_VERSION_0_3 = MOBILEDOC_VERSION_0_3;\n var MOBILEDOC_VERSION_0_3_1 = '0.3.1';\n exports.MOBILEDOC_VERSION_0_3_1 = MOBILEDOC_VERSION_0_3_1;\n var MOBILEDOC_VERSION = MOBILEDOC_VERSION_0_3_1;\n\n exports.MOBILEDOC_VERSION = MOBILEDOC_VERSION;\n function validateVersion(version) {\n if (version !== MOBILEDOC_VERSION_0_3 && version !== MOBILEDOC_VERSION_0_3_1) {\n throw new Error('Unexpected Mobiledoc version \"' + version + '\"');\n }\n }\n\n var Renderer = (function () {\n function Renderer(mobiledoc, state) {\n _classCallCheck(this, Renderer);\n\n var cards = state.cards;\n var cardOptions = state.cardOptions;\n var atoms = state.atoms;\n var unknownCardHandler = state.unknownCardHandler;\n var unknownAtomHandler = state.unknownAtomHandler;\n var version = mobiledoc.version;\n var sections = mobiledoc.sections;\n var atomTypes = mobiledoc.atoms;\n var cardTypes = mobiledoc.cards;\n\n validateVersion(version);\n\n this.root = [];\n this.sections = sections;\n this.atomTypes = atomTypes;\n this.cardTypes = cardTypes;\n this.cards = cards;\n this.atoms = atoms;\n this.cardOptions = cardOptions;\n this.unknownCardHandler = unknownCardHandler || this._defaultUnknownCardHandler;\n this.unknownAtomHandler = unknownAtomHandler || this._defaultUnknownAtomHandler;\n\n this._teardownCallbacks = [];\n }\n\n _createClass(Renderer, [{\n key: 'render',\n value: function render() {\n var _this = this;\n\n this.sections.forEach(function (section) {\n _this.root.push(_this.renderSection(section));\n });\n\n var result = this.root.join(LINE_BREAK);\n return { result: result, teardown: function teardown() {\n return _this.teardown();\n } };\n }\n }, {\n key: 'teardown',\n value: function teardown() {\n for (var i = 0; i < this._teardownCallbacks.length; i++) {\n this._teardownCallbacks[i]();\n }\n }\n }, {\n key: 'renderSection',\n value: function renderSection(section) {\n var _section = _slicedToArray(section, 1);\n\n var type = _section[0];\n\n switch (type) {\n case _mobiledocTextRendererUtilsSectionTypes.MARKUP_SECTION_TYPE:\n return this.renderMarkupSection(section);\n case _mobiledocTextRendererUtilsSectionTypes.IMAGE_SECTION_TYPE:\n return this.renderImageSection(section);\n case _mobiledocTextRendererUtilsSectionTypes.LIST_SECTION_TYPE:\n return this.renderListSection(section);\n case _mobiledocTextRendererUtilsSectionTypes.CARD_SECTION_TYPE:\n return this.renderCardSection(section);\n default:\n throw new Error('Unimplemented renderer for type ' + type);\n }\n }\n }, {\n key: 'renderImageSection',\n value: function renderImageSection() {\n return '';\n }\n }, {\n key: 'renderListSection',\n value: function renderListSection(_ref) {\n var _this2 = this;\n\n var _ref2 = _slicedToArray(_ref, 3);\n\n var type = _ref2[0];\n var tagName = _ref2[1];\n var items = _ref2[2];\n\n return items.map(function (li) {\n return _this2.renderListItem(li);\n }).join(LINE_BREAK);\n }\n }, {\n key: 'renderListItem',\n value: function renderListItem(markers) {\n return this.renderMarkers(markers);\n }\n }, {\n key: 'findCard',\n value: function findCard(name) {\n for (var i = 0; i < this.cards.length; i++) {\n if (this.cards[i].name === name) {\n return this.cards[i];\n }\n }\n if (name === _mobiledocTextRendererCardsImage['default'].name) {\n return _mobiledocTextRendererCardsImage['default'];\n }\n return this._createUnknownCard(name);\n }\n }, {\n key: '_findCardByIndex',\n value: function _findCardByIndex(index) {\n var cardType = this.cardTypes[index];\n if (!cardType) {\n throw new Error('No card definition found at index ' + index);\n }\n\n var _cardType = _slicedToArray(cardType, 2);\n\n var name = _cardType[0];\n var payload = _cardType[1];\n\n var card = this.findCard(name);\n\n return {\n card: card,\n payload: payload\n };\n }\n }, {\n key: '_createUnknownCard',\n value: function _createUnknownCard(name) {\n return {\n name: name,\n type: _mobiledocTextRendererUtilsRenderType['default'],\n render: this.unknownCardHandler\n };\n }\n }, {\n key: 'renderCardSection',\n value: function renderCardSection(_ref3) {\n var _ref32 = _slicedToArray(_ref3, 2);\n\n var type = _ref32[0];\n var index = _ref32[1];\n\n var _findCardByIndex2 = this._findCardByIndex(index);\n\n var card = _findCardByIndex2.card;\n var payload = _findCardByIndex2.payload;\n\n var cardArg = this._createCardArgument(card, payload);\n var rendered = card.render(cardArg);\n\n this._validateCardRender(rendered, card.name);\n\n return rendered || '';\n }\n }, {\n key: '_validateCardRender',\n value: function _validateCardRender(rendered, cardName) {\n if (!rendered) {\n return;\n }\n\n if (typeof rendered !== 'string') {\n throw new Error('Card \"' + cardName + '\" must render ' + _mobiledocTextRendererUtilsRenderType['default'] + ', but result was ' + typeof rendered + '\"');\n }\n }\n }, {\n key: '_registerTeardownCallback',\n value: function _registerTeardownCallback(callback) {\n this._teardownCallbacks.push(callback);\n }\n }, {\n key: '_createCardArgument',\n value: function _createCardArgument(card) {\n var _this3 = this;\n\n var payload = arguments.length <= 1 || arguments[1] === undefined ? {} : arguments[1];\n\n var env = {\n name: card.name,\n isInEditor: false,\n onTeardown: function onTeardown(callback) {\n return _this3._registerTeardownCallback(callback);\n }\n };\n\n var options = this.cardOptions;\n\n return { env: env, options: options, payload: payload };\n }\n }, {\n key: 'renderMarkupSection',\n value: function renderMarkupSection(_ref4) {\n var _ref42 = _slicedToArray(_ref4, 3);\n\n var type = _ref42[0];\n var tagName = _ref42[1];\n var markers = _ref42[2];\n\n return this.renderMarkers(markers);\n }\n }, {\n key: 'findAtom',\n value: function findAtom(name) {\n for (var i = 0; i < this.atoms.length; i++) {\n if (this.atoms[i].name === name) {\n return this.atoms[i];\n }\n }\n return this._createUnknownAtom(name);\n }\n }, {\n key: '_createUnknownAtom',\n value: function _createUnknownAtom(name) {\n return {\n name: name,\n type: _mobiledocTextRendererUtilsRenderType['default'],\n render: this.unknownAtomHandler\n };\n }\n }, {\n key: '_createAtomArgument',\n value: function _createAtomArgument(atom, value, payload) {\n var _this4 = this;\n\n var env = {\n name: atom.name,\n onTeardown: function onTeardown(callback) {\n return _this4._registerTeardownCallback(callback);\n }\n };\n\n var options = this.cardOptions;\n\n return { env: env, options: options, value: value, payload: payload };\n }\n }, {\n key: '_validateAtomRender',\n value: function _validateAtomRender(rendered, atomName) {\n if (!rendered) {\n return;\n }\n\n if (typeof rendered !== 'string') {\n throw new Error('Atom \"' + atomName + '\" must render ' + _mobiledocTextRendererUtilsRenderType['default'] + ', but result was ' + typeof rendered + '\"');\n }\n }\n }, {\n key: '_findAtomByIndex',\n value: function _findAtomByIndex(index) {\n var atomType = this.atomTypes[index];\n if (!atomType) {\n throw new Error('No atom definition found at index ' + index);\n }\n\n var _atomType = _slicedToArray(atomType, 3);\n\n var name = _atomType[0];\n var value = _atomType[1];\n var payload = _atomType[2];\n\n var atom = this.findAtom(name);\n\n return {\n atom: atom,\n value: value,\n payload: payload\n };\n }\n }, {\n key: '_renderAtom',\n value: function _renderAtom(index) {\n var _findAtomByIndex2 = this._findAtomByIndex(index);\n\n var atom = _findAtomByIndex2.atom;\n var value = _findAtomByIndex2.value;\n var payload = _findAtomByIndex2.payload;\n\n var atomArg = this._createAtomArgument(atom, value, payload);\n var rendered = atom.render(atomArg);\n\n this._validateAtomRender(rendered, atom.name);\n\n return rendered || '';\n }\n }, {\n key: 'renderMarkers',\n value: function renderMarkers(markers) {\n var _this5 = this;\n\n var str = '';\n markers.forEach(function (m) {\n var _m = _slicedToArray(m, 4);\n\n var type = _m[0];\n var value = _m[3];\n\n switch (type) {\n case _mobiledocTextRendererUtilsMarkerTypes.MARKUP_MARKER_TYPE:\n str += value;\n break;\n case _mobiledocTextRendererUtilsMarkerTypes.ATOM_MARKER_TYPE:\n str += _this5._renderAtom(value);\n break;\n default:\n throw new Error('Unknown markup type (' + type + ')');\n }\n });\n return str;\n }\n }, {\n key: '_defaultUnknownCardHandler',\n get: function get() {\n return function () {\n // for the text renderer, a missing card is a no-op\n };\n }\n }, {\n key: '_defaultUnknownAtomHandler',\n get: function get() {\n return function (_ref5) {\n var value = _ref5.value;\n\n return value || '';\n };\n }\n }]);\n\n return Renderer;\n })();\n\n exports['default'] = Renderer;\n});","define(\"mobiledoc-text-renderer/utils/marker-types\", [\"exports\"], function (exports) {\n \"use strict\";\n\n var MARKUP_MARKER_TYPE = 0;\n exports.MARKUP_MARKER_TYPE = MARKUP_MARKER_TYPE;\n var ATOM_MARKER_TYPE = 1;\n exports.ATOM_MARKER_TYPE = ATOM_MARKER_TYPE;\n});","define('mobiledoc-text-renderer/utils/render-type', ['exports'], function (exports) {\n 'use strict';\n\n exports['default'] = 'text';\n});","define(\"mobiledoc-text-renderer/utils/section-types\", [\"exports\"], function (exports) {\n \"use strict\";\n\n var MARKUP_SECTION_TYPE = 1;\n exports.MARKUP_SECTION_TYPE = MARKUP_SECTION_TYPE;\n var IMAGE_SECTION_TYPE = 2;\n exports.IMAGE_SECTION_TYPE = IMAGE_SECTION_TYPE;\n var LIST_SECTION_TYPE = 3;\n exports.LIST_SECTION_TYPE = LIST_SECTION_TYPE;\n var CARD_SECTION_TYPE = 10;\n exports.CARD_SECTION_TYPE = CARD_SECTION_TYPE;\n});"],"names":[],"mappings":"AAAA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACdA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACVA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AChHA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AChWA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACreA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACbA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AChBA;AACA;AACA;AACA;AACA;AACA;AACA;;ACNA;AACA;AACA;AACA;;ACHA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AClCA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACvCA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACVA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACxCA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AChBA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AC/KA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AClKA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AC5wCA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACxVA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACjNA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACxLA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACh3CA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACnWA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACtIA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACjDA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACzFA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACnGA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACnFA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACvBA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACrWA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACjLA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACxFA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACzHA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AC3IA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AC/EA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACzCA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AC7EA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AC1DA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AC9GA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AC/JA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACvDA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACpEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACvMA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACjRA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACxIA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AC1GA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACpBA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AC1TA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACnCA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AC3MA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AC7RA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AC7RA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACrBA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AC/TA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACzGA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AC9nBA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACjHA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AC9IA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AC9IA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACrBA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACpMA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACPA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACVA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACRA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AC3CA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACXA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AChPA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACjjBA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AC1PA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACpBA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AClIA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AC7CA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACxEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACPA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AClDA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AC/RA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AC3CA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACZA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AClRA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AC9EA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACnHA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACxBA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AClBA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACnBA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AC/KA;AACA;AACA;AACA;AACA;AACA;;ACLA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACjPA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AChDA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AC/BA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACfA;AACA;AACA;AACA;;ACHA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AChEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AChFA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACPA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACVA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACxFA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;ACvOA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AC5WA;AACA;AACA;AACA;AACA;AACA;AACA;;ACNA;AACA;AACA;AACA;;ACHA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;","file":"mobiledoc-kit.js"} \ No newline at end of file diff --git a/website/commonjs/mobiledoc-kit/editor/edit-history.js b/website/commonjs/mobiledoc-kit/editor/edit-history.js index ce5e0c3d3..dfee6b1e5 100644 --- a/website/commonjs/mobiledoc-kit/editor/edit-history.js +++ b/website/commonjs/mobiledoc-kit/editor/edit-history.js @@ -21,11 +21,15 @@ function findLeafSectionAtIndex(post, index) { } var Snapshot = (function () { - function Snapshot(editor) { + function Snapshot(takenAt, editor) { + var editAction = arguments.length <= 2 || arguments[2] === undefined ? null : arguments[2]; + _classCallCheck(this, Snapshot); this.mobiledoc = editor.serialize(); this.editor = editor; + this.editAction = editAction; + this.takenAt = takenAt; this.snapshotRange(); } @@ -76,6 +80,11 @@ var Snapshot = (function () { return head.toRange(tail); } } + }, { + key: 'groupsWith', + value: function groupsWith(groupingTimeout, editAction, takenAt) { + return editAction !== null && this.editAction === editAction && this.takenAt + groupingTimeout > takenAt; + } }]); return Snapshot; @@ -84,7 +93,7 @@ var Snapshot = (function () { exports.Snapshot = Snapshot; var EditHistory = (function () { - function EditHistory(editor, queueLength) { + function EditHistory(editor, queueLength, groupingTimeout) { _classCallCheck(this, EditHistory); this.editor = editor; @@ -92,6 +101,7 @@ var EditHistory = (function () { this._redoStack = new _utilsFixedQueue['default'](queueLength); this._pendingSnapshot = null; + this._groupingTimeout = groupingTimeout; } _createClass(EditHistory, [{ @@ -105,14 +115,20 @@ var EditHistory = (function () { }, { key: 'storeSnapshot', value: function storeSnapshot() { + var editAction = arguments.length <= 0 || arguments[0] === undefined ? null : arguments[0]; + + var now = Date.now(); // store pending snapshot - if (this._pendingSnapshot) { - this._undoStack.push(this._pendingSnapshot); + var pendingSnapshot = this._pendingSnapshot; + if (pendingSnapshot) { + if (!pendingSnapshot.groupsWith(this._groupingTimeout, editAction, now)) { + this._undoStack.push(pendingSnapshot); + } this._redoStack.clear(); } // take new pending snapshot to store next time `storeSnapshot` is called - this._pendingSnapshot = new Snapshot(this.editor); + this._pendingSnapshot = new Snapshot(now, this.editor, editAction); } }, { key: 'stepBackward', @@ -122,7 +138,7 @@ var EditHistory = (function () { var snapshot = this._undoStack.pop(); if (snapshot) { - this._redoStack.push(new Snapshot(this.editor)); + this._redoStack.push(new Snapshot(Date.now(), this.editor)); this._restoreFromSnapshot(snapshot, postEditor); } } @@ -131,7 +147,7 @@ var EditHistory = (function () { value: function stepForward(postEditor) { var snapshot = this._redoStack.pop(); if (snapshot) { - this._undoStack.push(new Snapshot(this.editor)); + this._undoStack.push(new Snapshot(Date.now(), this.editor)); this._restoreFromSnapshot(snapshot, postEditor); } postEditor.cancelSnapshot(); diff --git a/website/commonjs/mobiledoc-kit/editor/editor.js b/website/commonjs/mobiledoc-kit/editor/editor.js index 1de57e3c8..2d6dc803c 100644 --- a/website/commonjs/mobiledoc-kit/editor/editor.js +++ b/website/commonjs/mobiledoc-kit/editor/editor.js @@ -38,6 +38,8 @@ var _utilsCursorRange = require('../utils/cursor/range'); var _utilsCursorPosition = require('../utils/cursor/position'); +var _utilsEnvironment = require('../utils/environment'); + var _modelsPostNodeBuilder = require('../models/post-node-builder'); var _textInputHandlers = require('./text-input-handlers'); @@ -56,7 +58,7 @@ var _editorEventManager = require('../editor/event-manager'); var _editorEditState = require('../editor/edit-state'); -var _mobiledocHtmlRenderer = require('mobiledoc-html-renderer'); +var _mobiledocDomRenderer = require('mobiledoc-dom-renderer'); var _mobiledocTextRenderer = require('mobiledoc-text-renderer'); @@ -82,6 +84,7 @@ var defaults = { spellcheck: true, autofocus: true, undoDepth: 5, + undoBlockTimeout: 5000, // ms for an undo event cards: [], atoms: [], cardOptions: {}, @@ -192,7 +195,7 @@ var Editor = (function () { this.post = this.loadPost(); this._renderTree = new _modelsRenderTree['default'](this.post); - this._editHistory = new _editorEditHistory['default'](this, this.undoDepth); + this._editHistory = new _editorEditHistory['default'](this, this.undoDepth, this.undoBlockTimeout); this._eventManager = new _editorEventManager['default'](this); this._mutationHandler = new _editorMutationHandler['default'](this); this._editState = new _editorEditState['default'](this); @@ -350,6 +353,22 @@ var Editor = (function () { this.keyCommands.unshift(keyCommand); } + /** + * @param {String} name If the keyCommand event has a name attribute it can be removed. + * @public + */ + }, { + key: 'unregisterKeyCommands', + value: function unregisterKeyCommands(name) { + for (var i = this.keyCommands.length - 1; i > -1; i--) { + var keyCommand = this.keyCommands[i]; + + if (keyCommand.name === name) { + this.keyCommands.splice(i, 1); + } + } + } + /** * Convenience for {@link PostEditor#deleteAtPosition}. Deletes and puts the * cursor in the new position. @@ -633,8 +652,15 @@ var Editor = (function () { switch (format) { case 'html': - rendered = new _mobiledocHtmlRenderer['default'](rendererOptions).render(mobiledoc); - return rendered.result; + var result = undefined; + if (_utilsEnvironment['default'].hasDOM()) { + rendered = new _mobiledocDomRenderer['default'](rendererOptions).render(mobiledoc); + result = '
' + (0, _utilsDomUtils.serializeHTML)(rendered.result) + '
'; + } else { + // Fallback to text serialization + result = this.serializePost(post, 'text', options); + } + return result; case 'text': rendered = new _mobiledocTextRenderer['default'](rendererOptions).render(mobiledoc); return rendered.result; @@ -794,7 +820,7 @@ var Editor = (function () { if (postEditor._shouldCancelSnapshot) { this._editHistory._pendingSnapshot = null; } - this._editHistory.storeSnapshot(); + this._editHistory.storeSnapshot(postEditor.editActionTaken); return result; } diff --git a/website/commonjs/mobiledoc-kit/editor/key-commands.js b/website/commonjs/mobiledoc-kit/editor/key-commands.js index 4db33ad5c..73ed53b89 100644 --- a/website/commonjs/mobiledoc-kit/editor/key-commands.js +++ b/website/commonjs/mobiledoc-kit/editor/key-commands.js @@ -76,6 +76,16 @@ var DEFAULT_KEY_COMMANDS = [{ run: function run(editor) { editor.toggleMarkup('em'); } +}, { + str: 'META+U', + run: function run(editor) { + editor.toggleMarkup('u'); + } +}, { + str: 'CTRL+U', + run: function run(editor) { + editor.toggleMarkup('u'); + } }, { str: 'CTRL+K', run: function run(editor) { diff --git a/website/commonjs/mobiledoc-kit/editor/post.js b/website/commonjs/mobiledoc-kit/editor/post.js index c167929a1..7146daf12 100644 --- a/website/commonjs/mobiledoc-kit/editor/post.js +++ b/website/commonjs/mobiledoc-kit/editor/post.js @@ -39,6 +39,14 @@ var CALLBACK_QUEUES = { AFTER_COMPLETE: 'afterComplete' }; +// There are only two events that we're concerned about for Undo, that is inserting text and deleting content. +// These are the only two states that go on a "run" and create a combined undo, everything else has it's own +// deadicated undo. +var EDIT_ACTIONS = { + INSERT_TEXT: 1, + DELETE: 2 +}; + /** * The PostEditor is used to modify a post. It should not be instantiated directly. * Instead, a new instance of a PostEditor is created by the editor and passed @@ -68,6 +76,7 @@ var PostEditor = (function () { this._callbacks = new _modelsLifecycleCallbacks['default']((0, _utilsArrayUtils.values)(CALLBACK_QUEUES)); this._didComplete = false; + this.editActionTaken = null; this._renderRange = function () { return _this.editor.selectRange(_this._range); @@ -157,6 +166,8 @@ var PostEditor = (function () { value: function deleteRange(range) { (0, _utilsAssert['default'])("Must pass MobiledocKit Range to `deleteRange`", range instanceof _utilsCursorRange['default']); + this.editActionTaken = EDIT_ACTIONS.DELETE; + var head = range.head; var headSection = range.head.section; var tail = range.tail; @@ -688,6 +699,8 @@ var PostEditor = (function () { (0, _utilsAssert['default'])('Cannot insert markers at non-markerable position', section.isMarkerable); + this.editActionTaken = EDIT_ACTIONS.INSERT_TEXT; + var edit = section.splitMarkerAtOffset(offset); edit.removed.forEach(function (marker) { return _this9._scheduleForRemoval(marker); diff --git a/website/commonjs/mobiledoc-kit/editor/text-input-handlers.js b/website/commonjs/mobiledoc-kit/editor/text-input-handlers.js index a82dfdd60..bd38c0e5a 100644 --- a/website/commonjs/mobiledoc-kit/editor/text-input-handlers.js +++ b/website/commonjs/mobiledoc-kit/editor/text-input-handlers.js @@ -42,7 +42,7 @@ function replaceWithListSection(editor, listTagName) { * Does nothing if the cursor position is not at the start of the section. * * @param {Editor} editor - * @param {String} headingTagName ("h1","h2","h3") + * @param {String} headingTagName ('h1', 'h2', 'h3', 'h4', 'h5', 'h6') * @public */ @@ -81,8 +81,15 @@ var DEFAULT_TEXT_INPUT_HANDLERS = [{ } }, { name: 'heading', - // "# " -> h1, "## " -> h2, "### " -> h3 - match: /^(#{1,3}) $/, + /* + * "# " -> h1 + * "## " -> h2 + * "### " -> h3 + * "#### " -> h4 + * "##### " -> h5 + * "###### " -> h6 + */ + match: /^(#{1,6}) $/, run: function run(editor, matches) { var capture = matches[1]; var headingTag = 'h' + capture.length; diff --git a/website/commonjs/mobiledoc-kit/models/markup-section.js b/website/commonjs/mobiledoc-kit/models/markup-section.js index 51740e43f..f5e883a8d 100644 --- a/website/commonjs/mobiledoc-kit/models/markup-section.js +++ b/website/commonjs/mobiledoc-kit/models/markup-section.js @@ -17,15 +17,15 @@ var _utilsArrayUtils = require('../utils/array-utils'); var _types = require('./types'); // valid values of `tagName` for a MarkupSection -var VALID_MARKUP_SECTION_TAGNAMES = ['p', 'h3', 'h2', 'h1', 'blockquote', 'pull-quote'].map(_utilsDomUtils.normalizeTagName); +var VALID_MARKUP_SECTION_TAGNAMES = ['aside', 'blockquote', 'h1', 'h2', 'h3', 'h4', 'h5', 'h6', 'p'].map(_utilsDomUtils.normalizeTagName); exports.VALID_MARKUP_SECTION_TAGNAMES = VALID_MARKUP_SECTION_TAGNAMES; // valid element names for a MarkupSection. A MarkupSection with a tagName // not in this will be rendered as a div with a className matching the // tagName -var MARKUP_SECTION_ELEMENT_NAMES = ['p', 'h3', 'h2', 'h1', 'blockquote'].map(_utilsDomUtils.normalizeTagName); +var MARKUP_SECTION_ELEMENT_NAMES = ['aside', 'blockquote', 'h1', 'h2', 'h3', 'h4', 'h5', 'h6', 'p'].map(_utilsDomUtils.normalizeTagName); exports.MARKUP_SECTION_ELEMENT_NAMES = MARKUP_SECTION_ELEMENT_NAMES; -var DEFAULT_TAG_NAME = VALID_MARKUP_SECTION_TAGNAMES[0]; +var DEFAULT_TAG_NAME = VALID_MARKUP_SECTION_TAGNAMES[8]; exports.DEFAULT_TAG_NAME = DEFAULT_TAG_NAME; var MarkupSection = (function (_Markerable) { diff --git a/website/commonjs/mobiledoc-kit/models/markup.js b/website/commonjs/mobiledoc-kit/models/markup.js index 7f4e1f320..75eeddc37 100644 --- a/website/commonjs/mobiledoc-kit/models/markup.js +++ b/website/commonjs/mobiledoc-kit/models/markup.js @@ -12,13 +12,13 @@ var _types = require('./types'); var _utilsAssert = require('../utils/assert'); -var VALID_MARKUP_TAGNAMES = ['b', 'i', 'strong', 'em', 'a', 'u', 'sub', // subscript +var VALID_MARKUP_TAGNAMES = ['a', 'b', 'code', 'em', 'i', 's', // strikethrough +'strong', 'sub', // subscript 'sup', // superscript -'s' // strikethrough -].map(_utilsDomUtils.normalizeTagName); +'u'].map(_utilsDomUtils.normalizeTagName); exports.VALID_MARKUP_TAGNAMES = VALID_MARKUP_TAGNAMES; -var VALID_ATTRIBUTES = ['href', 'ref']; +var VALID_ATTRIBUTES = ['href', 'rel']; exports.VALID_ATTRIBUTES = VALID_ATTRIBUTES; diff --git a/website/commonjs/mobiledoc-kit/parsers/mobiledoc/0-2.js b/website/commonjs/mobiledoc-kit/parsers/mobiledoc/0-2.js index ebbd1fe07..feb4e8880 100644 --- a/website/commonjs/mobiledoc-kit/parsers/mobiledoc/0-2.js +++ b/website/commonjs/mobiledoc-kit/parsers/mobiledoc/0-2.js @@ -134,7 +134,7 @@ var MobiledocParser = (function () { var tagName = _ref52[1]; var markers = _ref52[2]; - var section = this.builder.createMarkupSection(tagName); + var section = this.builder.createMarkupSection(tagName.toLowerCase() === 'pull-quote' ? 'aside' : tagName); post.sections.append(section); this.parseMarkers(markers, section); // Strip blank markers after they have been created. This ensures any diff --git a/website/commonjs/mobiledoc-kit/parsers/mobiledoc/0-3-1.js b/website/commonjs/mobiledoc-kit/parsers/mobiledoc/0-3-1.js new file mode 100644 index 000000000..6b50c8825 --- /dev/null +++ b/website/commonjs/mobiledoc-kit/parsers/mobiledoc/0-3-1.js @@ -0,0 +1,291 @@ +'use strict'; + +var _slicedToArray = (function () { function sliceIterator(arr, i) { var _arr = []; var _n = true; var _d = false; var _e = undefined; try { for (var _i = arr[Symbol.iterator](), _s; !(_n = (_s = _i.next()).done); _n = true) { _arr.push(_s.value); if (i && _arr.length === i) break; } } catch (err) { _d = true; _e = err; } finally { try { if (!_n && _i['return']) _i['return'](); } finally { if (_d) throw _e; } } return _arr; } return function (arr, i) { if (Array.isArray(arr)) { return arr; } else if (Symbol.iterator in Object(arr)) { return sliceIterator(arr, i); } else { throw new TypeError('Invalid attempt to destructure non-iterable instance'); } }; })(); + +var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })(); + +function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError('Cannot call a class as a function'); } } + +var _renderersMobiledoc031 = require('../../renderers/mobiledoc/0-3-1'); + +var _utilsArrayUtils = require("../../utils/array-utils"); + +var _utilsAssert = require('../../utils/assert'); + +/* + * Parses from mobiledoc -> post + */ + +var MobiledocParser = (function () { + function MobiledocParser(builder) { + _classCallCheck(this, MobiledocParser); + + this.builder = builder; + } + + /** + * @param {Mobiledoc} + * @return {Post} + */ + + _createClass(MobiledocParser, [{ + key: 'parse', + value: function parse(_ref) { + var version = _ref.version; + var sections = _ref.sections; + var markerTypes = _ref.markups; + var cardTypes = _ref.cards; + var atomTypes = _ref.atoms; + + try { + var post = this.builder.createPost(); + + this.markups = []; + this.markerTypes = this.parseMarkerTypes(markerTypes); + this.cardTypes = this.parseCardTypes(cardTypes); + this.atomTypes = this.parseAtomTypes(atomTypes); + this.parseSections(sections, post); + + return post; + } catch (e) { + (0, _utilsAssert['default'])('Unable to parse mobiledoc: ' + e.message, false); + } + } + }, { + key: 'parseMarkerTypes', + value: function parseMarkerTypes(markerTypes) { + var _this = this; + + return markerTypes.map(function (markerType) { + return _this.parseMarkerType(markerType); + }); + } + }, { + key: 'parseMarkerType', + value: function parseMarkerType(_ref2) { + var _ref22 = _slicedToArray(_ref2, 2); + + var tagName = _ref22[0]; + var attributesArray = _ref22[1]; + + var attributesObject = (0, _utilsArrayUtils.kvArrayToObject)(attributesArray || []); + return this.builder.createMarkup(tagName, attributesObject); + } + }, { + key: 'parseCardTypes', + value: function parseCardTypes(cardTypes) { + var _this2 = this; + + return cardTypes.map(function (cardType) { + return _this2.parseCardType(cardType); + }); + } + }, { + key: 'parseCardType', + value: function parseCardType(_ref3) { + var _ref32 = _slicedToArray(_ref3, 2); + + var cardName = _ref32[0]; + var cardPayload = _ref32[1]; + + return [cardName, cardPayload]; + } + }, { + key: 'parseAtomTypes', + value: function parseAtomTypes(atomTypes) { + var _this3 = this; + + return atomTypes.map(function (atomType) { + return _this3.parseAtomType(atomType); + }); + } + }, { + key: 'parseAtomType', + value: function parseAtomType(_ref4) { + var _ref42 = _slicedToArray(_ref4, 3); + + var atomName = _ref42[0]; + var atomValue = _ref42[1]; + var atomPayload = _ref42[2]; + + return [atomName, atomValue, atomPayload]; + } + }, { + key: 'parseSections', + value: function parseSections(sections, post) { + var _this4 = this; + + sections.forEach(function (section) { + return _this4.parseSection(section, post); + }); + } + }, { + key: 'parseSection', + value: function parseSection(section, post) { + var _section = _slicedToArray(section, 1); + + var type = _section[0]; + + switch (type) { + case _renderersMobiledoc031.MOBILEDOC_MARKUP_SECTION_TYPE: + this.parseMarkupSection(section, post); + break; + case _renderersMobiledoc031.MOBILEDOC_IMAGE_SECTION_TYPE: + this.parseImageSection(section, post); + break; + case _renderersMobiledoc031.MOBILEDOC_CARD_SECTION_TYPE: + this.parseCardSection(section, post); + break; + case _renderersMobiledoc031.MOBILEDOC_LIST_SECTION_TYPE: + this.parseListSection(section, post); + break; + default: + (0, _utilsAssert['default'])('Unexpected section type ${type}', false); + } + } + }, { + key: 'getAtomTypeFromIndex', + value: function getAtomTypeFromIndex(index) { + var atomType = this.atomTypes[index]; + (0, _utilsAssert['default'])('No atom definition found at index ' + index, !!atomType); + return atomType; + } + }, { + key: 'getCardTypeFromIndex', + value: function getCardTypeFromIndex(index) { + var cardType = this.cardTypes[index]; + (0, _utilsAssert['default'])('No card definition found at index ' + index, !!cardType); + return cardType; + } + }, { + key: 'parseCardSection', + value: function parseCardSection(_ref5, post) { + var _ref52 = _slicedToArray(_ref5, 2); + + var type = _ref52[0]; + var cardIndex = _ref52[1]; + + var _getCardTypeFromIndex = this.getCardTypeFromIndex(cardIndex); + + var _getCardTypeFromIndex2 = _slicedToArray(_getCardTypeFromIndex, 2); + + var name = _getCardTypeFromIndex2[0]; + var payload = _getCardTypeFromIndex2[1]; + + var section = this.builder.createCardSection(name, payload); + post.sections.append(section); + } + }, { + key: 'parseImageSection', + value: function parseImageSection(_ref6, post) { + var _ref62 = _slicedToArray(_ref6, 2); + + var type = _ref62[0]; + var src = _ref62[1]; + + var section = this.builder.createImageSection(src); + post.sections.append(section); + } + }, { + key: 'parseMarkupSection', + value: function parseMarkupSection(_ref7, post) { + var _ref72 = _slicedToArray(_ref7, 3); + + var type = _ref72[0]; + var tagName = _ref72[1]; + var markers = _ref72[2]; + + var section = this.builder.createMarkupSection(tagName); + post.sections.append(section); + this.parseMarkers(markers, section); + // Strip blank markers after they have been created. This ensures any + // markup they include has been correctly populated. + (0, _utilsArrayUtils.filter)(section.markers, function (m) { + return m.isBlank; + }).forEach(function (m) { + section.markers.remove(m); + }); + } + }, { + key: 'parseListSection', + value: function parseListSection(_ref8, post) { + var _ref82 = _slicedToArray(_ref8, 3); + + var type = _ref82[0]; + var tagName = _ref82[1]; + var items = _ref82[2]; + + var section = this.builder.createListSection(tagName); + post.sections.append(section); + this.parseListItems(items, section); + } + }, { + key: 'parseListItems', + value: function parseListItems(items, section) { + var _this5 = this; + + items.forEach(function (i) { + return _this5.parseListItem(i, section); + }); + } + }, { + key: 'parseListItem', + value: function parseListItem(markers, section) { + var item = this.builder.createListItem(); + this.parseMarkers(markers, item); + section.items.append(item); + } + }, { + key: 'parseMarkers', + value: function parseMarkers(markers, parent) { + var _this6 = this; + + markers.forEach(function (m) { + return _this6.parseMarker(m, parent); + }); + } + }, { + key: 'parseMarker', + value: function parseMarker(_ref9, parent) { + var _this7 = this; + + var _ref92 = _slicedToArray(_ref9, 4); + + var type = _ref92[0]; + var markerTypeIndexes = _ref92[1]; + var closeCount = _ref92[2]; + var value = _ref92[3]; + + markerTypeIndexes.forEach(function (index) { + _this7.markups.push(_this7.markerTypes[index]); + }); + + var marker = this.buildMarkerType(type, value); + parent.markers.append(marker); + + this.markups = this.markups.slice(0, this.markups.length - closeCount); + } + }, { + key: 'buildMarkerType', + value: function buildMarkerType(type, value) { + switch (type) { + case _renderersMobiledoc031.MOBILEDOC_MARKUP_MARKER_TYPE: + return this.builder.createMarker(value, this.markups.slice()); + case _renderersMobiledoc031.MOBILEDOC_ATOM_MARKER_TYPE: + var _getAtomTypeFromIndex = this.getAtomTypeFromIndex(value), + _getAtomTypeFromIndex2 = _slicedToArray(_getAtomTypeFromIndex, 3), + atomName = _getAtomTypeFromIndex2[0], + atomValue = _getAtomTypeFromIndex2[1], + atomPayload = _getAtomTypeFromIndex2[2]; + + return this.builder.createAtom(atomName, atomValue, atomPayload, this.markups.slice()); + default: + (0, _utilsAssert['default'])('Unexpected marker type ' + type, false); + } + } + }]); + + return MobiledocParser; +})(); + +exports['default'] = MobiledocParser; \ No newline at end of file diff --git a/website/commonjs/mobiledoc-kit/parsers/mobiledoc/0-3.js b/website/commonjs/mobiledoc-kit/parsers/mobiledoc/0-3.js index afe79e731..bb5feb4dc 100644 --- a/website/commonjs/mobiledoc-kit/parsers/mobiledoc/0-3.js +++ b/website/commonjs/mobiledoc-kit/parsers/mobiledoc/0-3.js @@ -195,7 +195,7 @@ var MobiledocParser = (function () { var tagName = _ref72[1]; var markers = _ref72[2]; - var section = this.builder.createMarkupSection(tagName); + var section = this.builder.createMarkupSection(tagName.toLowerCase() === 'pull-quote' ? 'aside' : tagName); post.sections.append(section); this.parseMarkers(markers, section); // Strip blank markers after they have been created. This ensures any diff --git a/website/commonjs/mobiledoc-kit/parsers/mobiledoc/index.js b/website/commonjs/mobiledoc-kit/parsers/mobiledoc/index.js index 29e70acf0..77369a78b 100644 --- a/website/commonjs/mobiledoc-kit/parsers/mobiledoc/index.js +++ b/website/commonjs/mobiledoc-kit/parsers/mobiledoc/index.js @@ -4,10 +4,14 @@ var _ = require('./0-2'); var _2 = require('./0-3'); +var _3 = require('./0-3-1'); + var _renderersMobiledoc02 = require('../../renderers/mobiledoc/0-2'); var _renderersMobiledoc03 = require('../../renderers/mobiledoc/0-3'); +var _renderersMobiledoc031 = require('../../renderers/mobiledoc/0-3-1'); + var _utilsAssert = require('../../utils/assert'); function parseVersion(mobiledoc) { @@ -22,6 +26,8 @@ exports['default'] = { return new _['default'](builder).parse(mobiledoc); case _renderersMobiledoc03.MOBILEDOC_VERSION: return new _2['default'](builder).parse(mobiledoc); + case _renderersMobiledoc031.MOBILEDOC_VERSION: + return new _3['default'](builder).parse(mobiledoc); default: (0, _utilsAssert['default'])('Unknown version of mobiledoc parser requested: ' + version, false); } diff --git a/website/commonjs/mobiledoc-kit/renderers/mobiledoc/0-3-1.js b/website/commonjs/mobiledoc-kit/renderers/mobiledoc/0-3-1.js new file mode 100644 index 000000000..1a00200a3 --- /dev/null +++ b/website/commonjs/mobiledoc-kit/renderers/mobiledoc/0-3-1.js @@ -0,0 +1,148 @@ +'use strict'; + +var _visitor; + +function _defineProperty(obj, key, value) { if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; } + +var _utilsCompiler = require('../../utils/compiler'); + +var _utilsArrayUtils = require('../../utils/array-utils'); + +var _modelsTypes = require('../../models/types'); + +var MOBILEDOC_VERSION = '0.3.1'; +exports.MOBILEDOC_VERSION = MOBILEDOC_VERSION; +var MOBILEDOC_MARKUP_SECTION_TYPE = 1; +exports.MOBILEDOC_MARKUP_SECTION_TYPE = MOBILEDOC_MARKUP_SECTION_TYPE; +var MOBILEDOC_IMAGE_SECTION_TYPE = 2; +exports.MOBILEDOC_IMAGE_SECTION_TYPE = MOBILEDOC_IMAGE_SECTION_TYPE; +var MOBILEDOC_LIST_SECTION_TYPE = 3; +exports.MOBILEDOC_LIST_SECTION_TYPE = MOBILEDOC_LIST_SECTION_TYPE; +var MOBILEDOC_CARD_SECTION_TYPE = 10; + +exports.MOBILEDOC_CARD_SECTION_TYPE = MOBILEDOC_CARD_SECTION_TYPE; +var MOBILEDOC_MARKUP_MARKER_TYPE = 0; +exports.MOBILEDOC_MARKUP_MARKER_TYPE = MOBILEDOC_MARKUP_MARKER_TYPE; +var MOBILEDOC_ATOM_MARKER_TYPE = 1; + +exports.MOBILEDOC_ATOM_MARKER_TYPE = MOBILEDOC_ATOM_MARKER_TYPE; +var visitor = (_visitor = {}, _defineProperty(_visitor, _modelsTypes.POST_TYPE, function (node, opcodes) { + opcodes.push(['openPost']); + (0, _utilsCompiler.visitArray)(visitor, node.sections, opcodes); +}), _defineProperty(_visitor, _modelsTypes.MARKUP_SECTION_TYPE, function (node, opcodes) { + opcodes.push(['openMarkupSection', node.tagName]); + (0, _utilsCompiler.visitArray)(visitor, node.markers, opcodes); +}), _defineProperty(_visitor, _modelsTypes.LIST_SECTION_TYPE, function (node, opcodes) { + opcodes.push(['openListSection', node.tagName]); + (0, _utilsCompiler.visitArray)(visitor, node.items, opcodes); +}), _defineProperty(_visitor, _modelsTypes.LIST_ITEM_TYPE, function (node, opcodes) { + opcodes.push(['openListItem']); + (0, _utilsCompiler.visitArray)(visitor, node.markers, opcodes); +}), _defineProperty(_visitor, _modelsTypes.IMAGE_SECTION_TYPE, function (node, opcodes) { + opcodes.push(['openImageSection', node.src]); +}), _defineProperty(_visitor, _modelsTypes.CARD_TYPE, function (node, opcodes) { + opcodes.push(['openCardSection', node.name, node.payload]); +}), _defineProperty(_visitor, _modelsTypes.MARKER_TYPE, function (node, opcodes) { + opcodes.push(['openMarker', node.closedMarkups.length, node.value]); + (0, _utilsCompiler.visitArray)(visitor, node.openedMarkups, opcodes); +}), _defineProperty(_visitor, _modelsTypes.MARKUP_TYPE, function (node, opcodes) { + opcodes.push(['openMarkup', node.tagName, (0, _utilsArrayUtils.objectToSortedKVArray)(node.attributes)]); +}), _defineProperty(_visitor, _modelsTypes.ATOM_TYPE, function (node, opcodes) { + opcodes.push(['openAtom', node.closedMarkups.length, node.name, node.value, node.payload]); + (0, _utilsCompiler.visitArray)(visitor, node.openedMarkups, opcodes); +}), _visitor); + +var postOpcodeCompiler = { + openMarker: function openMarker(closeCount, value) { + this.markupMarkerIds = []; + this.markers.push([MOBILEDOC_MARKUP_MARKER_TYPE, this.markupMarkerIds, closeCount, value || '']); + }, + openMarkupSection: function openMarkupSection(tagName) { + this.markers = []; + this.sections.push([MOBILEDOC_MARKUP_SECTION_TYPE, tagName, this.markers]); + }, + openListSection: function openListSection(tagName) { + this.items = []; + this.sections.push([MOBILEDOC_LIST_SECTION_TYPE, tagName, this.items]); + }, + openListItem: function openListItem() { + this.markers = []; + this.items.push(this.markers); + }, + openImageSection: function openImageSection(url) { + this.sections.push([MOBILEDOC_IMAGE_SECTION_TYPE, url]); + }, + openCardSection: function openCardSection(name, payload) { + var index = this._addCardTypeIndex(name, payload); + this.sections.push([MOBILEDOC_CARD_SECTION_TYPE, index]); + }, + openAtom: function openAtom(closeCount, name, value, payload) { + var index = this._addAtomTypeIndex(name, value, payload); + this.markupMarkerIds = []; + this.markers.push([MOBILEDOC_ATOM_MARKER_TYPE, this.markupMarkerIds, closeCount, index]); + }, + openPost: function openPost() { + this.atomTypes = []; + this.cardTypes = []; + this.markerTypes = []; + this.sections = []; + this.result = { + version: MOBILEDOC_VERSION, + atoms: this.atomTypes, + cards: this.cardTypes, + markups: this.markerTypes, + sections: this.sections + }; + }, + openMarkup: function openMarkup(tagName, attributes) { + var index = this._findOrAddMarkerTypeIndex(tagName, attributes); + this.markupMarkerIds.push(index); + }, + _addCardTypeIndex: function _addCardTypeIndex(cardName, payload) { + var cardType = [cardName, payload]; + this.cardTypes.push(cardType); + return this.cardTypes.length - 1; + }, + _addAtomTypeIndex: function _addAtomTypeIndex(atomName, atomValue, payload) { + var atomType = [atomName, atomValue, payload]; + this.atomTypes.push(atomType); + return this.atomTypes.length - 1; + }, + _findOrAddMarkerTypeIndex: function _findOrAddMarkerTypeIndex(tagName, attributesArray) { + if (!this._markerTypeCache) { + this._markerTypeCache = {}; + } + var key = tagName + '-' + attributesArray.join('-'); + + var index = this._markerTypeCache[key]; + if (index === undefined) { + var markerType = [tagName]; + if (attributesArray.length) { + markerType.push(attributesArray); + } + this.markerTypes.push(markerType); + + index = this.markerTypes.length - 1; + this._markerTypeCache[key] = index; + } + + return index; + } +}; + +/** + * Render from post -> mobiledoc + */ +exports['default'] = { + /** + * @param {Post} + * @return {Mobiledoc} + */ + render: function render(post) { + var opcodes = []; + (0, _utilsCompiler.visit)(visitor, post, opcodes); + var compiler = Object.create(postOpcodeCompiler); + (0, _utilsCompiler.compile)(compiler, opcodes); + return compiler.result; + } +}; \ No newline at end of file diff --git a/website/commonjs/mobiledoc-kit/renderers/mobiledoc/index.js b/website/commonjs/mobiledoc-kit/renderers/mobiledoc/index.js index b08bb3332..a4beb6846 100644 --- a/website/commonjs/mobiledoc-kit/renderers/mobiledoc/index.js +++ b/website/commonjs/mobiledoc-kit/renderers/mobiledoc/index.js @@ -4,9 +4,11 @@ var _ = require('./0-2'); var _2 = require('./0-3'); +var _3 = require('./0-3-1'); + var _utilsAssert = require('../../utils/assert'); -var MOBILEDOC_VERSION = _2.MOBILEDOC_VERSION; +var MOBILEDOC_VERSION = _3.MOBILEDOC_VERSION; exports.MOBILEDOC_VERSION = MOBILEDOC_VERSION; exports['default'] = { @@ -14,10 +16,12 @@ exports['default'] = { switch (version) { case _.MOBILEDOC_VERSION: return _['default'].render(post); - case undefined: - case null: case _2.MOBILEDOC_VERSION: return _2['default'].render(post); + case undefined: + case null: + case _3.MOBILEDOC_VERSION: + return _3['default'].render(post); default: (0, _utilsAssert['default'])('Unknown version of mobiledoc renderer requested: ' + version, false); } diff --git a/website/commonjs/mobiledoc-kit/utils/cursor.js b/website/commonjs/mobiledoc-kit/utils/cursor.js index ad311b96d..8b93460ef 100644 --- a/website/commonjs/mobiledoc-kit/utils/cursor.js +++ b/website/commonjs/mobiledoc-kit/utils/cursor.js @@ -211,6 +211,9 @@ var Cursor = (function () { var selection = this.selection; var renderTree = this.renderTree; + var parentNode = this.editor.element; + selection = (0, _utilsSelectionUtils.constrainSelectionTo)(selection, parentNode); + var _comparePosition = (0, _utilsSelectionUtils.comparePosition)(selection); var headNode = _comparePosition.headNode; diff --git a/website/commonjs/mobiledoc-kit/utils/cursor/position.js b/website/commonjs/mobiledoc-kit/utils/cursor/position.js index 8126a1dfc..b633b4fd7 100644 --- a/website/commonjs/mobiledoc-kit/utils/cursor/position.js +++ b/website/commonjs/mobiledoc-kit/utils/cursor/position.js @@ -1,6 +1,6 @@ 'use strict'; -var _get = function get(_x4, _x5, _x6) { var _again = true; _function: while (_again) { var object = _x4, property = _x5, receiver = _x6; _again = false; if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { _x4 = parent; _x5 = property; _x6 = receiver; _again = true; desc = parent = undefined; continue _function; } } else if ('value' in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } } }; +var _get = function get(_x5, _x6, _x7) { var _again = true; _function: while (_again) { var object = _x5, property = _x6, receiver = _x7; _again = false; if (object === null) object = Function.prototype; var desc = Object.getOwnPropertyDescriptor(object, property); if (desc === undefined) { var parent = Object.getPrototypeOf(object); if (parent === null) { return undefined; } else { _x5 = parent; _x6 = property; _x7 = receiver; _again = true; desc = parent = undefined; continue _function; } } else if ('value' in desc) { return desc.value; } else { var getter = desc.get; if (getter === undefined) { return undefined; } return getter.call(receiver); } } }; var _createClass = (function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ('value' in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; })(); @@ -116,8 +116,9 @@ Position = (function () { */ value: function toRange() { var tail = arguments.length <= 0 || arguments[0] === undefined ? this : arguments[0]; + var direction = arguments.length <= 1 || arguments[1] === undefined ? null : arguments[1]; - return new _range['default'](this, tail); + return new _range['default'](this, tail, direction); } }, { key: 'markerIn', @@ -185,7 +186,7 @@ Position = (function () { } /** - * @return {Boolean} If this position is at the head of its section + * @return {Boolean} If this position is at the tail of its section */ }, { key: 'isTail', diff --git a/website/commonjs/mobiledoc-kit/utils/cursor/range.js b/website/commonjs/mobiledoc-kit/utils/cursor/range.js index d9b71bbf6..ef6500920 100644 --- a/website/commonjs/mobiledoc-kit/utils/cursor/range.js +++ b/website/commonjs/mobiledoc-kit/utils/cursor/range.js @@ -131,6 +131,41 @@ var Range = (function () { return this._collapse(direction); } } + + /** + * expand a range to all markers matching a given check + * + * @param {Function} detectMarker + * @return {Range} The expanded range + * + * @public + */ + }, { + key: 'expandByMarker', + value: function expandByMarker(detectMarker) { + var head = this.head; + var tail = this.tail; + var direction = this.direction; + var headSection = head.section; + + if (headSection !== tail.section) { + throw new Error('#expandByMarker does not work across sections. Perhaps you should confirm the range is collapsed'); + } + + var firstNotMatchingDetect = function firstNotMatchingDetect(i) { + return !detectMarker(i); + }; + + var headMarker = head.section.markers.detect(firstNotMatchingDetect, head.marker, true); + headMarker = headMarker && headMarker.next || head.marker; + var headPosition = new _position['default'](headSection, headSection.offsetOfMarker(headMarker)); + + var tailMarker = tail.section.markers.detect(firstNotMatchingDetect, tail.marker); + tailMarker = tailMarker && tailMarker.prev || tail.marker; + var tailPosition = new _position['default'](tail.section, tail.section.offsetOfMarker(tailMarker) + tailMarker.length); + + return headPosition.toRange(tailPosition, direction); + } }, { key: '_collapse', value: function _collapse(direction) { diff --git a/website/commonjs/mobiledoc-kit/utils/dom-utils.js b/website/commonjs/mobiledoc-kit/utils/dom-utils.js index f8fc8e808..bb035ba7e 100644 --- a/website/commonjs/mobiledoc-kit/utils/dom-utils.js +++ b/website/commonjs/mobiledoc-kit/utils/dom-utils.js @@ -111,6 +111,12 @@ function parseHTML(html) { return div; } +function serializeHTML(node) { + var div = document.createElement('div'); + div.appendChild(node); + return div.innerHTML; +} + exports.containsNode = containsNode; exports.clearChildNodes = clearChildNodes; exports.getAttributes = getAttributes; @@ -122,4 +128,5 @@ exports.normalizeTagName = normalizeTagName; exports.isTextNode = isTextNode; exports.isCommentNode = isCommentNode; exports.isElementNode = isElementNode; -exports.parseHTML = parseHTML; \ No newline at end of file +exports.parseHTML = parseHTML; +exports.serializeHTML = serializeHTML; \ No newline at end of file diff --git a/website/commonjs/mobiledoc-kit/utils/environment.js b/website/commonjs/mobiledoc-kit/utils/environment.js new file mode 100644 index 000000000..7d1e219c5 --- /dev/null +++ b/website/commonjs/mobiledoc-kit/utils/environment.js @@ -0,0 +1,7 @@ +'use strict'; + +exports['default'] = { + hasDOM: function hasDOM() { + return typeof document !== 'undefined'; + } +}; \ No newline at end of file diff --git a/website/commonjs/mobiledoc-kit/utils/linked-list.js b/website/commonjs/mobiledoc-kit/utils/linked-list.js index f6bd73c35..73343b6bc 100644 --- a/website/commonjs/mobiledoc-kit/utils/linked-list.js +++ b/website/commonjs/mobiledoc-kit/utils/linked-list.js @@ -186,12 +186,13 @@ var LinkedList = (function () { key: 'detect', value: function detect(callback) { var item = arguments.length <= 1 || arguments[1] === undefined ? this.head : arguments[1]; + var reverse = arguments.length <= 2 || arguments[2] === undefined ? false : arguments[2]; while (item) { if (callback(item)) { return item; } - item = item.next; + item = reverse ? item.prev : item.next; } } }, { diff --git a/website/commonjs/mobiledoc-kit/utils/selection-utils.js b/website/commonjs/mobiledoc-kit/utils/selection-utils.js index c2e93261a..ee637cdc4 100644 --- a/website/commonjs/mobiledoc-kit/utils/selection-utils.js +++ b/website/commonjs/mobiledoc-kit/utils/selection-utils.js @@ -95,6 +95,54 @@ function findOffsetInNode(_x, _x2) { } } +function constrainNodeTo(node, parentNode, existingOffset) { + var compare = parentNode.compareDocumentPosition(node); + if (compare & Node.DOCUMENT_POSITION_CONTAINED_BY) { + // the node is inside parentNode, do nothing + return { node: node, offset: existingOffset }; + } else if (compare & Node.DOCUMENT_POSITION_CONTAINS) { + // the node contains parentNode. This shouldn't happen. + return { node: node, offset: existingOffset }; + } else if (compare & Node.DOCUMENT_POSITION_PRECEDING) { + // node is before parentNode. return start of deepest first child + var child = parentNode.firstChild; + while (child.firstChild) { + child = child.firstChild; + } + return { node: child, offset: 0 }; + } else if (compare & Node.DOCUMENT_POSITION_FOLLOWING) { + // node is after parentNode. return end of deepest last child + var child = parentNode.lastChild; + while (child.lastChild) { + child = child.lastChild; + } + + var offset = (0, _utilsDomUtils.isTextNode)(child) ? child.textContent.length : 1; + return { node: child, offset: offset }; + } else { + return { node: node, offset: existingOffset }; + } +} + +/* + * Returns a new selection that is constrained within parentNode. + * If the anchorNode or focusNode are outside the parentNode, they are replaced with the beginning + * or end of the parentNode's children + */ +function constrainSelectionTo(selection, parentNode) { + var _constrainNodeTo = constrainNodeTo(selection.anchorNode, parentNode, selection.anchorOffset); + + var anchorNode = _constrainNodeTo.node; + var anchorOffset = _constrainNodeTo.offset; + + var _constrainNodeTo2 = constrainNodeTo(selection.focusNode, parentNode, selection.focusOffset); + + var focusNode = _constrainNodeTo2.node; + var focusOffset = _constrainNodeTo2.offset; + + return { anchorNode: anchorNode, anchorOffset: anchorOffset, focusNode: focusNode, focusOffset: focusOffset }; +} + function comparePosition(_x3) { var _again2 = true; @@ -193,4 +241,5 @@ function comparePosition(_x3) { exports.clearSelection = clearSelection; exports.comparePosition = comparePosition; -exports.findOffsetInNode = findOffsetInNode; \ No newline at end of file +exports.findOffsetInNode = findOffsetInNode; +exports.constrainSelectionTo = constrainSelectionTo; \ No newline at end of file diff --git a/website/commonjs/mobiledoc-kit/version.js b/website/commonjs/mobiledoc-kit/version.js index cba058a62..099134ede 100644 --- a/website/commonjs/mobiledoc-kit/version.js +++ b/website/commonjs/mobiledoc-kit/version.js @@ -1,3 +1,3 @@ 'use strict'; -exports['default'] = '0.10.11'; \ No newline at end of file +exports['default'] = '0.10.16'; \ No newline at end of file diff --git a/website/css/mobiledoc-kit.css b/website/css/mobiledoc-kit.css index ad03cc9fe..7c56c6447 100644 --- a/website/css/mobiledoc-kit.css +++ b/website/css/mobiledoc-kit.css @@ -1,6 +1,7 @@ /** * Editor */ + .__mobiledoc-editor { font-family: 'Lora', Georgia, serif; margin: 1em 0; @@ -10,12 +11,15 @@ position: relative; min-height: 1em; } + .__mobiledoc-editor:focus { outline: none; } + .__mobiledoc-editor > * { position: relative; } + .__mobiledoc-editor.__has-no-content:after { content: attr(data-placeholder); color: #bbb; @@ -23,10 +27,12 @@ position: absolute; top: 0; } + .__mobiledoc-editor a { color: #0b8bff; white-space: nowrap; } + .__mobiledoc-editor h1, .__mobiledoc-editor h2, .__mobiledoc-editor h3, @@ -37,56 +43,60 @@ font-weight: 800; letter-spacing: -0.02em; } + .__mobiledoc-editor blockquote { border-left: 4px solid #0b8bff; margin: 1em 0 1em -1.2em; padding-left: 1.05em; color: #a0a0a0; } + .__mobiledoc-editor img { display: block; max-width: 100%; margin: 0 auto; } + .__mobiledoc-editor div, .__mobiledoc-editor iframe { max-width: 100%; } + +/** + * Cards + */ + .__mobiledoc-card { display: inline-block; } + /** - * Tooltip + * Tooltips */ + @-webkit-keyframes fade-in { - 0% { - opacity: 0; - } - 100% { - opacity: 1; - } + 0% { opacity: 0; } + 100% { opacity: 1; } } @keyframes fade-in { - 0% { - opacity: 0; - } - 100% { - opacity: 1; - } + 0% { opacity: 0; } + 100% { opacity: 1; } } + .__mobiledoc-tooltip { font-family: "Helvetica Neue", Helvetica, Arial, sans-serif; font-size: 0.7em; white-space: nowrap; position: absolute; - background-color: rgba(43, 43, 43, 0.9); + background-color: rgba(43,43,43,0.9); border-radius: 3px; line-height: 1em; padding: 0.7em 0.9em; color: #FFF; -webkit-animation: fade-in 0.2s; - animation: fade-in 0.2s; + animation: fade-in 0.2s; } + .__mobiledoc-tooltip:before { content: ''; position: absolute; @@ -95,12 +105,13 @@ height: 0; border-left: 0.4em solid transparent; border-right: 0.4em solid transparent; - border-bottom: 0.4em solid rgba(43, 43, 43, 0.9); + border-bottom: 0.4em solid rgba(43,43,43,0.9); top: -0.4em; margin-left: -0.4em; } + +/* help keeps mouseover state when moving from link to tooltip */ .__mobiledoc-tooltip:after { - /* help keeps mouseover state when moving from link to tooltip */ content: ''; position: absolute; left: 0; @@ -108,10 +119,12 @@ top: -0.4em; height: 0.4em; } + .__mobiledoc-tooltip a { color: #FFF; text-decoration: none; } + .__mobiledoc-tooltip a:hover { text-decoration: underline; } diff --git a/website/demo/debug.css b/website/demo/debug.css index 8e7f3ffc1..87ca6912e 100644 --- a/website/demo/debug.css +++ b/website/demo/debug.css @@ -1,3 +1,22 @@ #toolbar button.active { font-weight: bold; } + +#error { + color: red; +} + +#error .name { + font-weight: bold; +} + +#editor { + outline: 1px solid black; + width: 200px; + min-height: 300px; +} + +#editor[contenteditable="false"] { + color: #9e9e9e; + background-color: #f1f1f1; +} diff --git a/website/demo/debug.html b/website/demo/debug.html index 6b2f867f0..d64d01110 100644 --- a/website/demo/debug.html +++ b/website/demo/debug.html @@ -3,43 +3,68 @@ Mobiledoc Kit Debug - - - + + -
- - - - - - - -
- -
- -
-

Cursor

-
-
-
+

Mobiledoc Kit Debug Page

-
-

Post

-
+
+ + + + + + + +
-
-
-

Input Mode

-
+
+ +
+

Editor Info

+ +
+

Cursor

+
+
+
+ +
+

Post

+
+
+
+ +
+

Input Mode

+
+
+
+ +
+

Error

+
+ + +
+
-
+
+

Browser Info

+ +
+

Selection

+
+
+
+ diff --git a/website/demo/debug.js b/website/demo/debug.js index b5209c269..03f9890b3 100644 --- a/website/demo/debug.js +++ b/website/demo/debug.js @@ -5,6 +5,14 @@ var _slicedToArray = (function () { function sliceIterator(arr, i) { var _arr = var editor; +function renderError(event) { + var error = event.error; + $('#error .name').text(error.name); + $('#error .message').text(error.message); +} + +window.addEventListener('error', renderError); + function renderSection(section) { return '[' + 'Section: tagName ' + section.tagName + ' type: ' + section.type + ' isNested? ' + section.isNested + (section.isMarkerable ? ' Markers: ' + section.markers.length + ')' : '') + ']'; } @@ -26,6 +34,34 @@ function updateCursor() { $('#cursor').html(html); } +document.addEventListener('selectionchange', renderNativeSelection); + +function renderNativeSelection(event) { + var sel = window.getSelection(); + var anchorNode = sel.anchorNode; + var focusNode = sel.focusNode; + var anchorOffset = sel.anchorOffset; + var focusOffset = sel.focusOffset; + var isCollapsed = sel.isCollapsed; + var rangeCount = sel.rangeCount; + + if (anchorNode === null && focusNode === null) { + $('#selection').html('None'); + return; + } + $('#selection').html('\n
Anchor: ' + renderNode(anchorNode) + ' (' + anchorOffset + ')
\n
Focus: ' + renderNode(focusNode) + ' (' + focusOffset + ')
\n
' + (isCollapsed ? 'Collapsed' : 'Not collapsed') + '
\n
Ranges: ' + rangeCount + '
\n '); +} + +function renderNode(node) { + var text = node.textContent.slice(0, 22); + if (node.textContent.length > 22) { + text += '...'; + } + + var type = node.nodeType === Node.TEXT_NODE ? 'text' : 'el (' + node.tagName + ')'; + return '' + type + ': ' + text; +} + function renderMarkup(markup) { function renderAttrs(obj) { var str = Object.keys(obj).reduce(function (memo, key) { @@ -233,6 +269,18 @@ $(function () { editor[action](toggle); }); + $('#toolbar button.toggle-method').click(function () { + var isOn = $(this).data('is-on') === 'true'; + var methodOn = $(this).data('on'); + var methodOff = $(this).data('off'); + + var nextState = isOn ? 'false' : 'true'; + var method = isOn ? methodOff : methodOn; + + $(this).data('is-on', nextState); + editor[method](); + }); + $('#toolbar button.insert-atom').click(function () { var name = $(this).data('name'); var value = $(this).data('value') || ''; diff --git a/website/demo/docs/Editor.html b/website/demo/docs/Editor.html index 29ae8d930..490349708 100644 --- a/website/demo/docs/Editor.html +++ b/website/demo/docs/Editor.html @@ -629,7 +629,7 @@
Properties
Source:
@@ -723,7 +723,7 @@
Type:
Source:
@@ -795,7 +795,7 @@
Type:
Source:
@@ -867,7 +867,7 @@
Type:
Source:
@@ -929,7 +929,7 @@

rangeSource:
@@ -1008,7 +1008,7 @@

_hasFocusSource:
@@ -1116,7 +1116,7 @@

_hasSele
Source:
@@ -1269,7 +1269,7 @@

Parameters:
Source:
@@ -1352,7 +1352,7 @@

delet
Source:
@@ -1484,7 +1484,7 @@

Parameters:
Source:
@@ -1566,7 +1566,7 @@

destroySource:
@@ -1693,7 +1693,7 @@
Parameters:
Source:
@@ -1821,7 +1821,7 @@
Parameters:
Source:
@@ -1948,7 +1948,7 @@
Parameters:
Source:
@@ -2031,7 +2031,7 @@

disable
Source:
@@ -2120,7 +2120,7 @@

disable
Source:
@@ -2253,7 +2253,7 @@

Parameters:
Source:
@@ -2396,7 +2396,7 @@
Parameters:
Source:
@@ -2480,7 +2480,7 @@

enableEd
Source:
@@ -2638,7 +2638,7 @@

Parameters:
Source:
@@ -2768,7 +2768,7 @@
Parameters:
Source:
@@ -2871,7 +2871,7 @@

hasCursorSource:
@@ -3017,7 +3017,7 @@
Parameters:
Source:
@@ -3244,7 +3244,7 @@
Parameters:
Source:
@@ -3495,7 +3495,7 @@
Parameters:
Source:
@@ -3650,7 +3650,7 @@
Parameters:
Source:
@@ -3943,7 +3943,7 @@
Properties
Source:
@@ -4093,7 +4093,7 @@
Parameters:
Source:
@@ -4243,7 +4243,7 @@
Parameters:
Source:
@@ -4373,7 +4373,7 @@
Parameters:
Source:
@@ -4501,7 +4501,7 @@
Parameters:
Source:
@@ -4647,7 +4647,7 @@
Parameters:
Source:
@@ -4805,7 +4805,7 @@
Parameters:
Source:
@@ -4932,7 +4932,7 @@
Parameters:
Source:
@@ -5089,7 +5089,7 @@
Parameters:
Source:
@@ -5249,7 +5249,7 @@
Parameters:
Source:
@@ -5389,7 +5389,7 @@
Parameters:
Source:
@@ -5478,7 +5478,134 @@

Source:
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

unregisterKeyCommands(name)

+ + + + + + + + + + + + + +
Parameters:
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
NameTypeDescription
name + + +String + + + +

If the keyCommand event has a name attribute it can be removed.

+ + + + + + +
+ + + + + + + + + + + + + + + + + + + + + + + + + + +
Source:
+
@@ -5609,7 +5736,7 @@
Parameters:
Source:
@@ -5736,7 +5863,7 @@
Parameters:
Source:
@@ -5863,7 +5990,7 @@
Parameters:
Source:
@@ -5991,7 +6118,7 @@
Parameters:
Source:
@@ -6039,7 +6166,7 @@

Home

Modules