@themarioga/grid-editor 8.8.2 → 8.9.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +16 -0
- package/README.md +18 -0
- package/dist/grideditor.bundle.min.js +3 -3
- package/dist/grideditor.css +51 -0
- package/dist/grideditor.d.ts +28 -1
- package/dist/grideditor.esm.js +311 -20
- package/dist/grideditor.jquery.js +3 -1
- package/dist/grideditor.jquery.min.js +1 -1
- package/dist/grideditor.jquery.min.js.map +2 -2
- package/dist/grideditor.js +311 -20
- package/dist/grideditor.min.css +1 -1
- package/dist/grideditor.min.css.map +1 -1
- package/dist/grideditor.min.js +2 -2
- package/dist/grideditor.min.js.map +3 -3
- package/dist/locales/grideditor.es.esm.js +4 -0
- package/dist/locales/grideditor.es.js +4 -0
- package/dist/locales/grideditor.es.min.js +1 -1
- package/dist/locales/grideditor.es.min.js.map +2 -2
- package/docs/events.md +6 -0
- package/docs/locale-keys.md +4 -0
- package/docs/plugins.md +15 -1
- package/example/utilities.html +3 -1
- package/package.json +1 -1
- package/src/js/grideditor.jquery.js +2 -0
- package/src/js/grideditor.js +361 -29
- package/src/js/locales/grideditor.es.js +4 -0
- package/src/less/grideditor.less +59 -0
- package/types/grideditor.d.ts +28 -1
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"version": 3,
|
|
3
3
|
"sources": ["../src/js/dom.js", "../src/js/grideditor.js", "../src/js/grideditor.classic.js"],
|
|
4
|
-
"sourcesContent": ["/**\n * The DOM, the way grid-editor uses it.\n *\n * Small helpers over the browser's own API, for the core and the shipped\n * plugins. Not a public API: a plugin of a host's own is free to write its\n * DOM code however it likes, and this file makes no promise to it.\n *\n * Stateless on purpose. The build puts a copy of this file in each plugin's\n * classic script, so anything kept here would be kept once per copy; a\n * module that needs to remember something about a node keeps its own\n * WeakMap.\n */\n\n/** Every element under `root` matching `selector`, as an array. */\nexport function all(root, selector) {\n return root ? Array.prototype.slice.call(root.querySelectorAll(selector)) : [];\n}\n\n/** The first element under `root` matching `selector`, or null. */\nexport function one(root, selector) {\n return root ? root.querySelector(selector) : null;\n}\n\n/** `root` itself when it matches, then every element under it that does. */\nexport function selfAndAll(root, selector) {\n if (!root) { return []; }\n\n var found = all(root, selector);\n if (root.nodeType === 1 && root.matches(selector)) { found.unshift(root); }\n return found;\n}\n\n/** The element children of `node`, those matching `selector` if one is given. */\nexport function children(node, selector) {\n if (!node) { return []; }\n\n return Array.prototype.filter.call(node.children, function(each) {\n return !selector || each.matches(selector);\n });\n}\n\n/** The first element child matching `selector`, or null. */\nexport function child(node, selector) {\n return children(node, selector)[0] || null;\n}\n\n/** The nearest ancestor-or-self matching `selector` below `stopAt`, or null. */\nexport function closest(node, selector, stopAt) {\n var found = node && node.nodeType === 1 ? node.closest(selector) : null;\n\n if (found && stopAt && found !== stopAt && !stopAt.contains(found)) { return null; }\n return found;\n}\n\n/** Whether `node` is an element matching `selector`. */\nexport function is(node, selector) {\n return !!node && node.nodeType === 1 && node.matches(selector);\n}\n\n/** Whether `node` is in the document. */\nexport function attached(node) {\n return !!node && document.documentElement.contains(node);\n}\n\n/** The element siblings after `node` that match `selector`. */\nexport function nextAll(node, selector) {\n var found = [];\n\n for (var next = node.nextElementSibling; next; next = next.nextElementSibling) {\n if (!selector || next.matches(selector)) { found.push(next); }\n }\n return found;\n}\n\n/** The ancestors of `node` up to, and not including, `stop`, nearest first. */\nexport function parentsUntil(node, stop) {\n var found = [];\n\n for (var parent = node.parentElement; parent && parent !== stop; parent = parent.parentElement) {\n found.push(parent);\n }\n return found;\n}\n\n/**\n * The nodes the html parses into, detached. Parsed the way innerHTML parses,\n * so a <script> in it never runs, here or once it is in the page.\n */\nexport function parse(html) {\n var template = document.createElement('template');\n template.innerHTML = html;\n return Array.prototype.slice.call(template.content.childNodes);\n}\n\n/** The one element the html is, detached. */\nexport function create(html) {\n var nodes = parse(html.trim());\n\n for (var i = 0; i < nodes.length; i++) {\n if (nodes[i].nodeType === 1) { return nodes[i]; }\n }\n return null;\n}\n\n/** An element of `tag`, with `attributes` and `text`. */\nexport function element(tag, attributes, text) {\n var node = document.createElement(tag);\n\n Object.keys(attributes || {}).forEach(function(name) {\n var value = attributes[name];\n if (value !== null && value !== undefined && value !== false) { node.setAttribute(name, value); }\n });\n if (text !== undefined && text !== null) { node.textContent = text; }\n\n return node;\n}\n\n/** Replace what `node` holds with `html`. A <script> in it does not run. */\nexport function setHtml(node, html) {\n node.innerHTML = html === undefined || html === null ? '' : String(html);\n return node;\n}\n\n/** Add one or several space separated classes. */\nexport function addClass(node, names) {\n split(names).forEach(function(name) { node.classList.add(name); });\n return node;\n}\n\nexport function removeClass(node, names) {\n split(names).forEach(function(name) { node.classList.remove(name); });\n return node;\n}\n\n/** Each class on, or off, or flipped when `on` is not given. */\nexport function toggleClass(node, names, state) {\n split(names).forEach(function(name) {\n if (state === undefined) {\n node.classList.toggle(name);\n } else {\n node.classList.toggle(name, !!state);\n }\n });\n return node;\n}\n\nexport function hasClass(node, name) {\n return !!node && node.nodeType === 1 && node.classList.contains(name);\n}\n\nfunction split(names) {\n return String(names || '').split(/\\s+/).filter(Boolean);\n}\n\n/** Take the class attribute off when there is nothing left in it. */\nexport function dropEmptyClass(node) {\n if (!node.getAttribute('class')) { node.removeAttribute('class'); }\n return node;\n}\n\n/** Take the style attribute off when there is nothing left in it. */\nexport function dropEmptyStyle(node) {\n if (!node.getAttribute('style')) { node.removeAttribute('style'); }\n return node;\n}\n\n/** Set attributes; a null or undefined value takes the attribute off. */\nexport function attr(node, attributes) {\n Object.keys(attributes).forEach(function(name) {\n var value = attributes[name];\n\n if (value === null || value === undefined) {\n node.removeAttribute(name);\n } else {\n node.setAttribute(name, value);\n }\n });\n return node;\n}\n\n/**\n * Inline styles, by css property name. A number is pixels for the properties\n * that take a length, as jQuery had it; an empty string takes one off.\n */\nexport function css(node, styles) {\n Object.keys(styles).forEach(function(property) {\n var value = styles[property];\n\n if (typeof value === 'number' && !UNITLESS[property]) { value = value + 'px'; }\n node.style.setProperty(property, value === null || value === undefined ? '' : String(value));\n });\n return node;\n}\n\nvar UNITLESS = { opacity: true, 'z-index': true, 'flex-grow': true, 'flex-shrink': true, order: true };\n\n/** What an element of this tag shows as when nothing hides it. */\nvar defaultDisplays = {};\n\nfunction defaultDisplay(node) {\n var tag = node.nodeName;\n\n if (!defaultDisplays[tag]) {\n var probe = document.body.appendChild(document.createElement(tag));\n defaultDisplays[tag] = getComputedStyle(probe).display;\n probe.remove();\n if (defaultDisplays[tag] === 'none') { defaultDisplays[tag] = 'block'; }\n }\n return defaultDisplays[tag];\n}\n\n/** Show a node: its inline display:none off, and a display of its own if a stylesheet hides it. */\nexport function show(node) {\n node.style.removeProperty('display');\n if (getComputedStyle(node).display === 'none') { node.style.display = defaultDisplay(node); }\n return node;\n}\n\nexport function hide(node) {\n node.style.display = 'none';\n return node;\n}\n\n/** Show or hide; flip when `on` is not given. */\nexport function toggle(node, state) {\n if (state === undefined) { state = !visible(node); }\n return state ? show(node) : hide(node);\n}\n\n/** Whether a node takes up room: what jQuery's :visible meant. */\nexport function visible(node) {\n return !!(node.offsetWidth || node.offsetHeight || node.getClientRects().length);\n}\n\n/** The border box's width, fractions included. */\nexport function outerWidth(node) {\n return node.getBoundingClientRect().width;\n}\n\nexport function outerHeight(node) {\n return node.getBoundingClientRect().height;\n}\n\n/** The content box's height, which is what jQuery's height() gave. */\nexport function contentHeight(node) {\n var style = getComputedStyle(node);\n return node.clientHeight - parseFloat(style.paddingTop) - parseFloat(style.paddingBottom);\n}\n\n/** Where a node is on the page, not in the window. */\nexport function offset(node) {\n var box = node.getBoundingClientRect();\n return { top: box.top + window.pageYOffset, left: box.left + window.pageXOffset };\n}\n\n/** Its index among its parent's element children, those matching `selector` if given. */\nexport function indexIn(node, selector) {\n return children(node.parentElement, selector).indexOf(node);\n}\n\n/** Put `node` right after `reference`. */\nexport function insertAfter(node, reference) {\n reference.parentNode.insertBefore(node, reference.nextSibling);\n return node;\n}\n\n/** Replace `node` with what it holds. */\nexport function unwrap(node) {\n var parent = node.parentNode;\n\n while (node.firstChild) { parent.insertBefore(node.firstChild, node); }\n node.remove();\n}\n\n/** Put `node` inside `wrapper`, where `node` was. */\nexport function wrap(node, wrapper) {\n node.parentNode.insertBefore(wrapper, node);\n wrapper.appendChild(node);\n return wrapper;\n}\n\n/**\n * Listen on `root` for `types` (space separated) on descendants that match\n * `selector`, with `this` the matched element, as jQuery's delegated\n * handlers had it. Hands back the listener, for removeEventListener; a\n * signal in `options` removes it too.\n */\nexport function delegate(root, types, selector, handler, options) {\n var listener = function(event) {\n var match = closest(event.target, selector, root);\n if (match && root.contains(match)) { return handler.call(match, event); }\n return undefined;\n };\n\n split(types).forEach(function(type) { root.addEventListener(type, listener, options); });\n return listener;\n}\n\n/** Listen for several space separated event types with one handler. */\nexport function on(target, types, handler, options) {\n split(types).forEach(function(type) { target.addEventListener(type, handler, options); });\n return handler;\n}\n\nexport function off(target, types, handler, options) {\n split(types).forEach(function(type) { target.removeEventListener(type, handler, options); });\n}\n\n/** A mouse event of `type` sent to `node`, the way a pointer would. */\nexport function fire(node, type) {\n node.dispatchEvent(new MouseEvent(type, { bubbles: type !== 'mouseenter' && type !== 'mouseleave' }));\n}\n\n/* ------------------------------------------------------------------\n * Taking a node away, visibly.\n *\n * The durations are jQuery's: 400 ms unless the caller says otherwise. `done` runs once the node is out of sight, which is\n * when the caller removes it; a node that is already out of sight is done at\n * once, on the next task, as jQuery had it.\n * ------------------------------------------------------------------ */\n\nvar DEFAULT_DURATION = 400;\n\nfunction animateAway(node, frames, duration, done) {\n duration = duration === undefined ? DEFAULT_DURATION : duration;\n\n var finish = function() {\n hide(node);\n if (done) { done(); }\n };\n\n if (!visible(node) || !node.animate || duration <= 0) {\n window.setTimeout(finish, 0);\n return;\n }\n\n var animation = node.animate(frames(getComputedStyle(node)), {\n duration: duration,\n easing: 'ease-in-out',\n });\n var called = false;\n var once = function() {\n if (called) { return; }\n called = true;\n finish();\n };\n\n animation.onfinish = once;\n animation.oncancel = once;\n}\n\n/** Fold a node up to nothing, then hide it. */\nexport function slideUp(node, duration, done) {\n if (typeof duration === 'function') {\n done = duration;\n duration = undefined;\n }\n\n node.style.overflow = 'hidden';\n animateAway(node, function(style) {\n return [\n {\n height: style.height,\n paddingTop: style.paddingTop,\n paddingBottom: style.paddingBottom,\n marginTop: style.marginTop,\n marginBottom: style.marginBottom,\n },\n { height: '0px', paddingTop: '0px', paddingBottom: '0px', marginTop: '0px', marginBottom: '0px' },\n ];\n }, duration, function() {\n node.style.removeProperty('overflow');\n if (done) { done(); }\n });\n}\n\n/** Fade a node out, then hide it. */\nexport function fadeOut(node, duration, done) {\n animateAway(node, function(style) {\n return [{ opacity: style.opacity }, { opacity: 0 }];\n }, duration, done);\n}\n\n/** Fade and fold a node, in height and, with `width`, sideways too, then hide it. */\nexport function shrinkAway(node, duration, done, width) {\n node.style.overflow = 'hidden';\n animateAway(node, function(style) {\n var from = { opacity: style.opacity, height: style.height };\n var to = { opacity: 0, height: '0px' };\n\n if (width) {\n from.width = style.width;\n to.width = '0px';\n }\n return [from, to];\n }, duration, function() {\n node.style.removeProperty('overflow');\n if (done) { done(); }\n });\n}\n", "/**\n * Grid editor.\n *\n * A fork of https://github.com/Friendly-Pixel/grid-editor by Simon Epskamp,\n * maintained at https://github.com/themarioga/grid-editor.\n *\n * Plain DOM: nothing here needs jQuery. A page written against the jQuery\n * API loads grideditor.jquery.js beside this file.\n */\nimport * as dom from './dom.js';\n\n/**\n * The methods an instance has, and which of them hand back something other\n * than the instance: html, a view key, a created node. After destroy() every\n * one of them is a no-op that says so once, and the value methods answer\n * null - but for getHtml and getPlainHtml, which read the element as it is.\n */\nvar METHODS = {\n getHtml: { value: true },\n getPlainHtml: { value: true },\n init: {},\n deinit: {},\n reset: {},\n destroy: {},\n changeView: {},\n getView: { value: true },\n createRow: { value: true },\n createColumn: { value: true },\n createElement: { value: true },\n createText: { value: true },\n createSection: { value: true },\n createContainer: { value: true },\n addTab: { value: true },\n addAccordionItem: { value: true },\n addPane: { value: true },\n setLocale: {},\n getUtility: { value: true },\n setUtility: { value: true },\n getActiveTarget: { value: true },\n setActiveTarget: {},\n};\n\n/**\n * Where a create* call may put the node it just made. The first one given\n * wins, and giving none leaves the node detached for the host to place.\n */\nvar PLACEMENTS = ['appendTo', 'prependTo', 'insertAfter', 'insertBefore'];\n\n/**\n * Bootstrap 5's breakpoints, smallest first, which is the order the cascade\n * runs in: a size written for a tier applies to every wider tier that does not\n * override it. Every size and offset class grid-editor reads or writes comes\n * from this table, so adding a tier is a row here and nothing else.\n *\n * `infix` is what Bootstrap's utility classes put between the property and\n * the value - `order-md-2`, `d-none` - and is empty for the smallest tier.\n */\nvar BREAKPOINTS = [\n { key: 'xs', infix: '', colPrefix: 'col-', offsetPrefix: 'offset-', min: 0, preview: 400, labelKey: 'view.xs' },\n { key: 'sm', infix: 'sm', colPrefix: 'col-sm-', offsetPrefix: 'offset-sm-', min: 576, preview: 576, labelKey: 'view.sm' },\n { key: 'md', infix: 'md', colPrefix: 'col-md-', offsetPrefix: 'offset-md-', min: 768, preview: 768, labelKey: 'view.md' },\n { key: 'lg', infix: 'lg', colPrefix: 'col-lg-', offsetPrefix: 'offset-lg-', min: 992, preview: 992, labelKey: 'view.lg' },\n { key: 'xl', infix: 'xl', colPrefix: 'col-xl-', offsetPrefix: 'offset-xl-', min: 1200, preview: 1200, labelKey: 'view.xl' },\n { key: 'xxl', infix: 'xxl', colPrefix: 'col-xxl-', offsetPrefix: 'offset-xxl-', min: 1400, preview: null, labelKey: 'view.xxl' },\n];\n\n/**\n * The view that edits every tier at once. It is the default, and the one most\n * pages want: a layout that needs no per-device tuning is written once, as the\n * class with no breakpoint, and applies at every size.\n */\nvar ALL_VIEW = 'all';\nvar ALL_VIEW_LABEL_KEY = 'view.all';\n\n/** Every view key the dropdown can offer, in the order it offers them. */\nvar VIEW_KEYS = [ALL_VIEW].concat(BREAKPOINTS.map(function(tier) { return tier.key; }));\n\n\nvar MAX_COL_SIZE = 12;\nvar MAX_COL_OFFSET = 11;\n\n/**\n * The two sizes that are not a number of units: `equal` is Bootstrap's col,\n * which shares what the row has left with the other equal columns, and\n * `auto` is col-auto, as wide as its content.\n */\nvar FLEX_SIZES = ['equal', 'auto'];\n\n/** How many columns a row-cols class puts on a line. */\nvar ROW_COLS_VALUES = ['1', '2', '3', '4', '5', '6', 'auto'];\n\nfunction rowColsClass(tier, value) {\n return 'row-cols' + (tier.infix ? '-' + tier.infix : '') + '-' + value;\n}\n\nfunction isUnits(size) {\n return typeof size === 'number';\n}\n\n/** The class that gives a column `size` at one tier: col-md-4, col-md, col-md-auto. */\nfunction sizeClass(tier, size) {\n if (size === 'equal') { return tier.infix ? 'col-' + tier.infix : 'col'; }\n\n return tier.colPrefix + size;\n}\n\nfunction breakpoint(key) {\n for (var i = 0; i < BREAKPOINTS.length; i++) {\n if (BREAKPOINTS[i].key === key) { return BREAKPOINTS[i]; }\n }\n return null;\n}\n\n/**\n * The tier a view writes to. The all view writes the base class, the one\n * with no breakpoint, and takes the others off.\n */\nfunction tiersFor(view) {\n if (view === ALL_VIEW) { return [BREAKPOINTS[0]]; }\n\n var tier = breakpoint(view);\n return tier ? [tier] : [];\n}\n\nfunction labelKeyFor(view) {\n var tier = breakpoint(view);\n return tier ? tier.labelKey : ALL_VIEW_LABEL_KEY;\n}\n\n/**\n * Settings that are objects of grid-editor's own keys rather than something\n * the host owns outright. A host naming one of their keys means \"this one is\n * different\", not \"forget the others\", so these are filled in from their\n * defaults instead of being replaced wholesale.\n */\nvar NESTED_SETTINGS = {\n add_column: {\n size: 12, // What a click on the add column tool adds\n picker: true, // Holding it offers the sizes instead\n delay: 600, // How long to hold, in milliseconds\n },\n elements: {\n enabled: 'auto', // 'auto' turns them on when the page has any\n selector: '[data-ge-element]', // What the host marks an element with\n auto: false, // Treat every child of a content area as an element\n types: [], // The elements the toolbar offers: { type, html, label | labelKey, iconClass, group }\n },\n resize: {\n enabled: true, // The handle on the column's edge\n tools: true, // The narrower and wider tools in the column's drawer\n handles: 'e', // Which edges carry a handle: 'e', 'w', or 'e, w'\n balance: 'next', // 'next' takes the units out of the following column\n },\n indent: {\n tools: true, // The indent tools in the column's drawer\n },\n drag: {\n delay: 0, // Milliseconds to hold before a drag starts\n touch_delay: 100, // The same for touch, where 0 eats the page's scrolling\n threshold: 3, // Pixels of movement before a gesture counts as a drag\n animation: 150, // Milliseconds of reordering animation, 0 for none\n scroll: true, // Scroll the page when a drag reaches its edge\n },\n};\n\nvar warned = {};\n\n/** Editors on the page, counted so each one's sortable groups are its own. */\nvar editorCounter = 0;\n\n/** The editor on each canvas element, so there is never a second one. */\nvar instances = new WeakMap();\n\n/**\n * Translate one key.\n *\n * Lookup order is locale_strings, then the selected locale, then English,\n * then the key itself, so a missing string is a visible key and never an\n * empty tooltip. `params` fills {name} placeholders.\n *\n * Exposed as GridEditor.t for the plugins that have settings and no\n * instance of their own.\n */\nfunction translate(settings, key, params) {\n var locales = GridEditor.locales;\n var locale = locales[settings.locale] || {};\n var overrides = settings.locale_strings || {};\n var string = overrides[key];\n\n if (string === undefined) { string = locale[key]; }\n if (string === undefined) { string = locales.en[key]; }\n\n if (string === undefined) {\n warnOnce('locale:' + key, 'no string for \"' + key + '\" in any locale, showing the key');\n string = key;\n }\n\n return string.replace(/\\{(\\w+)\\}/g, function(placeholder, name) {\n return params && params[name] !== undefined ? params[name] : placeholder;\n });\n}\n\n/** Whether some locale has a string for the key, asked without the warning a missing one gets. */\nfunction hasString(settings, key) {\n var locales = GridEditor.locales;\n\n return (settings.locale_strings || {})[key] !== undefined ||\n (locales[settings.locale] || {})[key] !== undefined ||\n locales.en[key] !== undefined;\n}\n\nfunction warn(message) {\n if (window.console && window.console.warn) {\n window.console.warn('grid-editor: ' + message);\n }\n}\n\n/** Warn about something the host can only usefully be told about once. */\nfunction warnOnce(key, message) {\n if (warned[key]) { return; }\n warned[key] = true;\n warn(message);\n}\n\n/** A string in English, for the few things said before an editor has settings. */\nfunction english(key, params) {\n return translate({ locale: 'en' }, key, params);\n}\n\n/**\n * The element an editor goes on: an element, or the first one a selector\n * matches. Anything else is a mistake worth throwing for, since there is no\n * editor to hand back.\n */\nfunction targetElement(target) {\n if (typeof target === 'string') {\n var found = document.querySelector(target);\n if (!found) { throw new TypeError('grid-editor: no element matches ' + JSON.stringify(target)); }\n return found;\n }\n\n if (target && target.nodeType === 1) { return target; }\n\n throw new TypeError('grid-editor: the target is an element or a selector, not ' +\n (target === null ? 'null' : typeof target));\n}\n\n/** A node a caller handed in, as an element: an element, a selector's first match, or null. */\nfunction nodeFrom(node) {\n if (typeof node === 'string') { return document.querySelector(node); }\n return node && node.nodeType === 1 ? node : null;\n}\n\n/**\n * SortableJS, and Bootstrap's Modal, as the host provided them: assigned to\n * GridEditor by a page that imports them as modules, or the page's globals.\n */\nfunction sortableLibrary() {\n return GridEditor.Sortable || window.Sortable || null;\n}\n\nfunction modalLibrary() {\n var bootstrap = GridEditor.bootstrap || window.bootstrap;\n return bootstrap && bootstrap.Modal ? bootstrap.Modal : null;\n}\n\n/**\n * Html with grid-editor's own marking taken off: the ge-* classes, the\n * column class and the data-ge-* attributes. A div that was only there for\n * the editor - a content area, a bare element or container wrapper - is left\n * with nothing on it, and goes, its children taking its place.\n *\n * The marking is what lets the editor read its markup back, so this is for\n * publishing, not for saving something to edit again.\n */\nfunction plainHtml(html) {\n // Parsed in a document of its own, which is inert: no script in the\n // markup runs and no image starts loading while it is being cleaned\n var root = document.implementation.createHTMLDocument('').body;\n root.innerHTML = html;\n var emptied = [];\n\n dom.all(root, '*').forEach(function(node) {\n var marked = false;\n\n Array.prototype.slice.call(node.attributes).forEach(function(attribute) {\n if (attribute.name.indexOf('data-ge-') === 0) {\n node.removeAttribute(attribute.name);\n marked = true;\n }\n });\n\n var classes = (node.getAttribute('class') || '').split(/\\s+/).filter(Boolean);\n var kept = classes.filter(function(name) {\n return name !== 'column' && name.indexOf('ge-') !== 0;\n });\n if (kept.length !== classes.length) { marked = true; }\n if (kept.length) {\n node.setAttribute('class', kept.join(' '));\n } else {\n node.removeAttribute('class');\n }\n\n if (marked && node.tagName === 'DIV' && !node.attributes.length) {\n emptied.push(node);\n }\n });\n\n emptied.forEach(function(div) {\n dom.unwrap(div);\n });\n\n return root.innerHTML;\n}\n\n/**\n * An editor on `target`: an element, or the first one a selector matches.\n *\n * var ge = new GridEditor('#myGrid', { new_row_layouts: [[12], [6, 6]] });\n * var html = ge.getHtml();\n *\n * An element carries one editor at most: asked for a second, this hands back\n * the one it has, with the options it was made with, and says so once.\n */\nfunction GridEditor(target, options) {\n var element = targetElement(target);\n var existing = instances.get(element);\n\n if (existing) {\n if (!doubleWarned.has(element)) {\n doubleWarned.add(element);\n warn(english('warning.already_editing'));\n }\n return existing;\n }\n\n if (!(this instanceof GridEditor)) { return new GridEditor(element, options); }\n\n build(this, element, options || {});\n}\n\n/** The elements a second editor was asked for on, so each is told about once. */\nvar doubleWarned = new WeakSet();\n\nGridEditor.create = function(target, options) {\n return new GridEditor(target, options);\n};\n\n/** The editor on `target`, or null. */\nGridEditor.get = function(target) {\n var element = nodeFrom(target);\n return element ? instances.get(element) || null : null;\n};\n\nfunction build(instance, baseElem, optionsOrMethod) {\n\n var settings = Object.assign({\n 'new_row_layouts' : [ // Column layouts for add row buttons\n [12],\n [6, 6],\n [4, 4, 4],\n [3, 3, 3, 3],\n [2, 2, 2, 2, 2, 2],\n [2, 8, 2],\n [4, 8],\n [8, 4]\n ],\n 'row_classes' : [], // Preset class toggles, on top of the classes field\n 'col_classes' : [],\n 'col_tools' : [], /* Example:\n [ {\n title: 'Set background image',\n iconClass: 'bi bi-image',\n on: { click: function(event) {} }\n } ]\n */\n 'row_tools' : [],\n 'drag_handle' : 'tool', // 'tool' for the move tool, 'drawer' for the whole drawer\n 'toolbar_drag' : 'auto', // Drag the toolbar's buttons onto the canvas. 'auto' follows drag_handle\n 'toolbar_overflow' : 'menu', // What doesn't fit on one line: 'menu' behind a button, 'wrap' onto another line\n 'drawer_overflow' : 'menu', // The same for the drawers' tools: 'menu' behind a button, 'wrap' onto another line\n 'toolbar_groups' : false, // The add buttons in categories, one shown at a time, picked with tabs\n 'active_target' : false, // A click in a column makes it where the toolbar's buttons add\n 'element_tools' : [], // Host tools on element drawers, same shape as row_tools\n 'element_classes' : [], // Preset class toggles on an element's settings panel\n // content_types, text_tools and text_classes are the text editor\n // plugins' settings: see grideditor.text.js\n 'container_classes' : [], // The same, on a container's panel\n 'pane_classes' : [], // And on a tab's or an accordion item's\n 'container_tools' : [], // Host tools on container drawers\n 'tab_tools' : [], // Host tools on tab drawers\n 'accordion_tools' : [], // Host tools on accordion item drawers\n 'plugins' : null, // Plugins to use, of any kind; null means every one loaded\n 'row_cols' : true, // A row's \"columns per row\" field, row-cols-*\n 'utilities' : {}, // Options for the utility plugins, by plugin name\n 'elements' : NESTED_SETTINGS.elements, // Element level controls, below the column\n 'custom_filter' : '',\n 'valid_col_sizes' : [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 'equal', 'auto'],\n 'valid_col_offsets' : [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11],\n 'add_column' : NESTED_SETTINGS.add_column, // The add column tool\n 'layout_modes' : VIEW_KEYS.slice(), // Which views the dropdown offers\n 'default_view' : ALL_VIEW,\n 'resize' : NESTED_SETTINGS.resize, // Resizing a column by dragging its edge\n 'indent' : NESTED_SETTINGS.indent, // Indenting a column, offset-*\n 'source_textarea' : '',\n 'edit_source' : true, // The toolbar's button to edit the canvas as html\n 'locale' : 'en', // Code of a locale in GridEditor.locales\n 'locale_strings' : {}, // Overrides for individual keys\n 'callbacks' : {}, // before_*/after_* functions, the events by another route\n 'confirm_delete' : true, // Ask before deleting a row or a column\n 'settings_panel' : 'offcanvas', // Where a node's settings open: 'offcanvas', 'popover', 'modal' or 'inline'\n 'drag' : NESTED_SETTINGS.drag // How a drag behaves, whatever drives it\n }, optionsOrMethod);\n\n // Merged rather than replaced, so `elements: { auto: true }` keeps the\n // default selector instead of losing it\n Object.keys(NESTED_SETTINGS).forEach(function(name) {\n settings[name] = Object.assign({}, NESTED_SETTINGS[name], settings[name]);\n });\n\n\n // Elems\n var canvas,\n mainControls,\n wrapper, // controls wrapper\n addRowGroup,\n addContainerGroup,\n layoutDropdown,\n htmlTextArea\n ;\n var curView = settings.default_view; // Breakpoint key, or 'all'\n var confirmDialog = null; // The delete confirmation, built when first needed\n var sizePicker = null; // The open column size picker, if there is one\n var sourceOpen = false; // Whether the canvas is being edited as html\n var dropMarker = null; // The line showing where a dragged toolbar button would land\n var activeTarget = null; // The column or region the toolbar adds to, with active_target\n var toolbarLifetime = null; // Aborted when the toolbar is rebuilt or taken away\n var closeOverflowMenu = function() {}; // Folds the toolbar's overflow menu away, when it has one\n var refitToolbar = function() {}; // Works out again what the toolbar's overflow menu holds, when it has one\n var addButtons = []; // The toolbar's add buttons, in toolbar order: { button, home, group }\n var shownToolbar = {}; // Each feature plugin's toolbar items, as the toolbar was last built with them\n var toolbarGroup = null; // The category shown, with toolbar_groups. Kept when the toolbar is rebuilt\n var warnedHere = {}; // Some warnings are worth saying once per instance, not once per call\n var sortables = []; // Every list made sortable, so deinit destroys exactly those\n var instanceId = ++editorCounter; // Scopes the sortable groups to this editor\n var destroyed = false;\n\n // What the editor remembers about the nodes it edits, which used to\n // be jQuery data: a node's settings panel, a drag or a resize in\n // progress. Kept off the markup, and gone with the node.\n var detailsFor = new WeakMap(); // node -> its settings panel\n var moves = new WeakMap(); // dragged node -> { from, canceled }\n var resizes = new WeakMap(); // column -> { from, units }\n var sectionNodes = new WeakMap(); // Responsive section -> the node it edits\n var editableLabels = new WeakSet(); // labels made editable in place\n\n // Listeners the editor puts on things it does not own - the window,\n // the document, the canvas - taken off together by destroy()\n var lifetime = new AbortController();\n\n // Before anything else, because the instance hands the canvas to\n // hosts and the rest of setup() runs at the end of this function\n canvas = dom.addClass(baseElem, 'ge-canvas');\n\n function warnOnceHere(key, message) {\n if (warnedHere[key]) { return; }\n warnedHere[key] = true;\n warn(message);\n }\n\n /** This instance's strings, in the locale its settings asked for. */\n function t(key, params) {\n return translate(settings, key, params);\n }\n\n /**\n * Swap language at runtime. The controls carry their strings in\n * attributes, so they are rebuilt rather than patched.\n */\n function setLocale(code) {\n settings.locale = code;\n instance.settings = settingsCopy();\n\n removeConfirmModal();\n removeSettingsPanels();\n removeDialog();\n removeMainControls();\n createMainControls();\n reset();\n }\n\n var operationDepth = 0; // Operations running right now\n var deferredWork = []; // What handlers asked for while one was running\n\n /**\n * The payload every notification carries. Built here, and only here,\n * so no caller assembles one by hand and gets a field wrong.\n *\n * `parent` is where the node is going, or where it is coming from on a\n * delete, which is not the same as the node's parent while the node is\n * still detached - so an add passes it in.\n */\n function payloadFor(kind, node, extra) {\n return Object.assign({\n kind: kind,\n node: node,\n parent: node.parentElement,\n canvas: canvas,\n breakpoint: getView(),\n source: 'api',\n }, extra || {});\n }\n\n /**\n * Deliver one notification twice: as a DOM event on the canvas - the\n * specific name first, then the generic one - and as the matching\n * settings.callbacks entries. Everything is delivered whatever the\n * first listener says, and the answer is whether any of them canceled,\n * which only means something for a before-* notification.\n *\n * A listener that throws is the browser's to report: the other\n * listeners, the callbacks and the operation go on.\n */\n function emit(name, payload) {\n var names = [name];\n var generic = name.replace(/^(before|after)-add-.+$/, '$1-add');\n if (generic !== name) { names.push(generic); }\n\n var canceled = false;\n\n names.forEach(function(eventName) {\n var event = new CustomEvent('grideditor:' + eventName, {\n detail: payload,\n bubbles: true,\n cancelable: true,\n });\n if (!canvas.dispatchEvent(event)) { canceled = true; }\n });\n\n names.forEach(function(eventName) {\n var callback = settings.callbacks[eventName.replace(/-/g, '_')];\n if (typeof callback == 'function' && callback(payload) === false) {\n canceled = true;\n }\n });\n\n return !canceled;\n }\n\n /**\n * One operation, from its before-* notification to its after-* one.\n *\n * Anything a handler asks the editor to do while the operation runs is\n * queued and played back once it finishes, so a handler cannot reset\n * the canvas out from under the operation that called it.\n */\n function operate(body) {\n operationDepth++;\n try {\n return body();\n } finally {\n operationDepth--;\n if (operationDepth === 0) {\n while (deferredWork.length) {\n deferredWork.shift()();\n }\n }\n }\n }\n\n /** Run `work` now, or after the running operation if there is one. */\n function defer(work) {\n if (operationDepth === 0) {\n work();\n return;\n }\n\n deferredWork.push(work);\n }\n\n /**\n * Insert a node: ask, insert, bring the canvas up to date so the new\n * markup has its controls, then announce it. Hands back the node, or\n * null when a handler canceled.\n *\n * The update is init() rather than reset(): a reset deinitializes\n * every rich text editor on the canvas, and adding a row somewhere\n * else is no reason to close the editor the user is typing in.\n */\n function addNode(kind, node, insert, extra) {\n var name = addEventName(kind);\n\n return operate(function() {\n var payload = payloadFor(kind, node, extra);\n\n if (!emit('before-add-' + name, payload)) { return null; }\n\n insert();\n init();\n emit('after-add-' + name, payload);\n\n return node;\n });\n }\n\n /**\n * Every container type shares one pair of add events, with the\n * payload's kind saying which type it was: a host that cares about\n * containers binds one name, not three.\n */\n function addEventName(kind) {\n return GridEditor.containers[kind] ? 'container' : kind;\n }\n\n /**\n * Ask the user, in Bootstrap's own modal.\n *\n * Bootstrap is already a dependency of an editor for Bootstrap's grid,\n * and window.confirm cannot be styled, cannot be translated by us and\n * blocks the page while it is up. The modal lives outside the canvas,\n * so it is never part of what getHtml returns.\n *\n * A page that loaded Bootstrap's css but not its javascript still gets\n * asked - by the browser, as before. A page that imports Bootstrap as\n * a module hands its Modal over as GridEditor.bootstrap.\n */\n function askToDelete(message, whenConfirmed) {\n if (!settings.confirm_delete) {\n whenConfirmed();\n return;\n }\n\n confirmWith(message, { danger: true }, function(confirmed) {\n if (confirmed) { whenConfirmed(); }\n });\n }\n\n /**\n * ge.confirm(): a question of a plugin's own, in the same modal.\n * `answer` is called once: true for the ok button, false for cancel,\n * the close button or Escape, and null when the question goes\n * unanswered because the modal is taken away - setLocale, destroy, or\n * another question asked over it.\n */\n function confirmWith(message, options, answer) {\n options = options || {};\n var Modal = modalLibrary();\n\n if (!Modal) {\n answer(window.confirm(message));\n return;\n }\n\n var modal = confirmModal();\n var confirmed = false;\n var ok = dom.one(modal, '.ge-confirm-ok');\n\n // The question before this one, if it is still up, goes unanswered\n if (pendingAnswer) { pendingAnswer(null); }\n\n var settle = function(value) {\n if (pendingAnswer !== settle) { return; }\n pendingAnswer = null;\n answer(value);\n };\n pendingAnswer = settle;\n\n dom.one(modal, '.modal-title').textContent = options.title || t('confirm.title');\n dom.one(modal, '.ge-confirm-cancel').textContent = options.cancel || t('confirm.cancel');\n ok.textContent = options.ok || t('confirm.ok');\n dom.toggleClass(ok, 'btn-danger', !!options.danger);\n dom.toggleClass(ok, 'btn-primary', !options.danger);\n\n dom.one(modal, '.ge-confirm-message').textContent = message;\n ok.onclick = function() {\n confirmed = true;\n Modal.getInstance(modal).hide();\n };\n\n confirmHandlers.hidden = function() {\n // After the modal is out of the way, so the backdrop is not\n // sitting over the animation a delete runs\n settle(confirmed);\n };\n\n confirmHandlers.shown = function() {\n ok.focus();\n };\n\n Modal.getOrCreateInstance(modal).show();\n }\n\n // What the confirm modal does when Bootstrap says it is shown or\n // hidden: this question's answer, replaced by the next question's\n var confirmHandlers = { hidden: null, shown: null };\n var pendingAnswer = null; // The open question's answer, until it is given\n\n /** Built once per instance, and taken away again by destroy(). */\n function confirmModal() {\n if (confirmDialog) { return confirmDialog; }\n\n confirmDialog = dom.create(\n '<div class=\"modal fade ge-confirm\" tabindex=\"-1\" aria-hidden=\"true\">' +\n '<div class=\"modal-dialog modal-dialog-centered\">' +\n '<div class=\"modal-content\">' +\n '<div class=\"modal-header\">' +\n '<h5 class=\"modal-title\"></h5>' +\n '<button type=\"button\" class=\"btn-close\" data-bs-dismiss=\"modal\"></button>' +\n '</div>' +\n '<div class=\"modal-body\"><p class=\"ge-confirm-message\"></p></div>' +\n '<div class=\"modal-footer\">' +\n '<button type=\"button\" class=\"btn btn-secondary ge-confirm-cancel\" data-bs-dismiss=\"modal\"></button>' +\n '<button type=\"button\" class=\"btn btn-danger ge-confirm-ok\"></button>' +\n '</div>' +\n '</div>' +\n '</div>' +\n '</div>'\n );\n document.body.appendChild(confirmDialog);\n\n dom.one(confirmDialog, '.modal-title').textContent = t('confirm.title');\n dom.one(confirmDialog, '.btn-close').setAttribute('aria-label', t('confirm.cancel'));\n dom.one(confirmDialog, '.ge-confirm-cancel').textContent = t('confirm.cancel');\n dom.one(confirmDialog, '.ge-confirm-ok').textContent = t('confirm.ok');\n\n trackModal(confirmDialog);\n // Only while it is the modal asking: one being taken away -\n // setLocale builds another - finishes hiding after the next\n // question is up, and that answer is not its to give\n var asking = confirmDialog;\n confirmDialog.addEventListener('hidden.bs.modal', function() {\n if (asking === confirmDialog && confirmHandlers.hidden) { confirmHandlers.hidden(); }\n });\n confirmDialog.addEventListener('shown.bs.modal', function() {\n if (asking === confirmDialog && confirmHandlers.shown) { confirmHandlers.shown(); }\n });\n\n return confirmDialog;\n }\n\n /** The confirm modal is rebuilt in the new language on setLocale. */\n function removeConfirmModal() {\n if (!confirmDialog) { return; }\n\n // Its answer is not wanted any more: the editor it asked for is going\n confirmHandlers.hidden = null;\n confirmHandlers.shown = null;\n retireModal(confirmDialog);\n confirmDialog = null;\n\n // A plugin's question goes unanswered, and the plugin is told so\n if (pendingAnswer) { pendingAnswer(null); }\n }\n\n /**\n * Take a Bootstrap modal away. One out of sight goes at once. One that\n * is showing, or on its way in or out, is asked to hide and goes when\n * Bootstrap says it is hidden: Bootstrap finishes a transition on the\n * node it started it on, and a node taken away under it throws, and\n * leaves the page's body locked, with no scrolling.\n */\n function retireModal(panel) {\n var Modal = modalLibrary();\n var modal = Modal ? Modal.getInstance(panel) : null;\n var gone = false;\n var finish = function() {\n if (gone) { return; }\n gone = true;\n if (modal) { modal.dispose(); }\n panel.remove();\n };\n\n if (!modal || (!modalMoving.get(panel) && !dom.hasClass(panel, 'show'))) {\n finish();\n return;\n }\n\n panel.addEventListener('hidden.bs.modal', finish, { once: true });\n // Still on its way in, it ignores a hide: once it is in, it takes one\n panel.addEventListener('shown.bs.modal', function() { modal.hide(); }, { once: true });\n modal.hide();\n }\n\n /** Whether a modal is between Bootstrap's show and shown, or hide and hidden. */\n var modalMoving = new WeakMap();\n\n function trackModal(panel) {\n dom.on(panel, 'show.bs.modal hide.bs.modal', function() { modalMoving.set(panel, true); });\n dom.on(panel, 'shown.bs.modal hidden.bs.modal', function() { modalMoving.set(panel, false); });\n }\n\n /**\n * Remove a node: ask the host, then the user, then remove it, update\n * the canvas and announce it once the animation has finished.\n *\n * The host's handler goes first on purpose. A host that cancels\n * before-delete to ask in its own way does not want the built-in\n * question to have been asked already.\n */\n function deleteNode(kind, node, message, animate) {\n operate(function() {\n var payload = payloadFor(kind, node, { source: 'tool' });\n\n if (!emit('before-delete', payload)) { return; }\n\n askToDelete(message, function() {\n operate(function() {\n animate(function() {\n node.remove();\n operate(function() {\n init();\n emit('after-delete', payload);\n });\n });\n });\n });\n });\n }\n\n /**\n * What resizing this column to `size` in `view` would write, or null\n * when the budget refuses it or there is nothing to change.\n *\n * A breakpoint view writes its own tier. The all view writes the base\n * class and takes the size off every other tier, so one size is what\n * applies everywhere; the plan says what it took off.\n *\n * Refused rather than quietly clamped: the offset is something the\n * user set, and a tool that rewrites it is a tool that lies. In the\n * all view the base size has to fit every tier's offset, since it is\n * the size at every tier once the others are gone.\n */\n function planSize(col, size, view) {\n view = view || curView;\n\n if (view !== ALL_VIEW) {\n var tier = breakpoint(view);\n var wanted = clamp({ size: size, offset: getEffectiveOffset(col, tier) || 0 });\n\n if (wanted.refused || getSize(col, tier) === wanted.size) { return null; }\n\n return { writes: [{ tier: tier, size: wanted.size }], cleared: null, size: wanted.size };\n }\n\n var refused = BREAKPOINTS.some(function(each) {\n return clamp({ size: size, offset: getEffectiveOffset(col, each) || 0 }).refused;\n });\n if (refused) { return null; }\n\n var base = BREAKPOINTS[0];\n var writes = [];\n var cleared = [];\n\n BREAKPOINTS.slice(1).forEach(function(each) {\n var own = getSize(col, each);\n if (own === null) { return; }\n\n writes.push({ tier: each, size: null });\n cleared.push({ breakpoint: each.key, value: own });\n });\n\n if (getSize(col, base) !== size) { writes.unshift({ tier: base, size: size }); }\n\n return writes.length ? { writes: writes, cleared: cleared, size: size } : null;\n }\n\n function writeSize(col, plan) {\n plan.writes.forEach(function(write) { setSize(col, write.tier, write.size); });\n stripPixelWidths(col);\n }\n\n /** The all view's payloads say what the write took off the breakpoints. */\n function withCleared(extra, cleared) {\n if (cleared) { extra.cleared = cleared; }\n return extra;\n }\n\n /**\n * Resize a column, announcing it either side. `size` is units,\n * `equal` or `auto`; `view` is the current one unless the size field\n * of a plugin's panel says otherwise.\n */\n function resizeColumn(col, size, source, view) {\n view = view || curView;\n\n var from = currentSize(col);\n var plan = planSize(col, size, view);\n\n if (!plan) { return false; }\n\n return operate(function() {\n var payload = payloadFor('column', col, withCleared({\n source: source,\n breakpoint: view,\n from: from,\n to: plan.size,\n }, plan.cleared));\n\n if (!emit('before-resize', payload)) {\n refreshUtilities(col);\n return false;\n }\n\n writeSize(col, plan);\n refreshUtilities(col);\n emit('after-resize', payload);\n\n return true;\n });\n }\n\n /**\n * Indent a column, shrinking it when the budget needs it: the offset\n * is what the user asked for, so it is the one that gets its way.\n *\n * Like a size, an offset is written to the tier being edited, or in\n * the all view as the base class with every other tier's taken off.\n */\n function indentColumn(col, offset, source) {\n var everywhere = curView === ALL_VIEW;\n var tier = everywhere ? BREAKPOINTS[0] : breakpoint(curView);\n var from = currentOffset(col);\n\n offset = Math.min(Math.max(offset, 0), MAX_COL_OFFSET);\n\n var others = everywhere ? BREAKPOINTS.slice(1).filter(function(each) {\n return getOffset(col, each) !== null;\n }) : [];\n\n if ((getOffset(col, tier) || 0) === offset && !others.length) { return false; }\n\n return operate(function() {\n var payload = payloadFor('column', col, withCleared({\n source: source,\n from: from,\n to: offset,\n }, everywhere ? others.map(function(each) {\n return { breakpoint: each.key, value: getOffset(col, each) };\n }) : null));\n\n if (!emit('before-indent', payload)) { return false; }\n\n setOffset(col, tier, offset);\n others.forEach(function(each) { setOffset(col, each, 0); });\n\n // Wherever the column's size and the new offset no longer fit\n // - one tier, or every tier in the all view - the size gives\n // way, at that tier only. An equal or auto column fits anywhere.\n (everywhere ? BREAKPOINTS : [tier]).forEach(function(each) {\n var was = getEffectiveSize(col, each);\n if (!isUnits(was)) { return; }\n\n var wanted = clamp({ size: was, offset: offset, leading: 'offset' });\n if (wanted.size !== was) { setSize(col, each, wanted.size); }\n });\n\n refreshUtilities(col);\n emit('after-indent', payload);\n\n return true;\n });\n }\n\n /**\n * Where a node sits, for the from/to of a move. Tool drawers are not\n * counted, so the index is the one a host would recognize.\n */\n function positionOf(node) {\n var parent = node.parentElement;\n\n return {\n parent: parent,\n index: dom.children(parent).filter(function(child) {\n return !dom.hasClass(child, 'ge-tools-drawer');\n }).indexOf(node),\n };\n }\n\n function kindOf(node) {\n var fromPlugin = null;\n\n Object.keys(FEATURES).forEach(function(name) {\n var feature = FEATURES[name];\n if (!fromPlugin && feature.kindOf) { fromPlugin = feature.kindOf(node); }\n });\n if (fromPlugin) { return fromPlugin; }\n\n if (node.getAttribute('data-ge-container')) { return node.getAttribute('data-ge-container'); }\n\n // A container plugin's pane, by the class it marks its panes with\n var paneKind = null;\n Object.keys(CONTAINERS).forEach(function(type) {\n var definition = CONTAINERS[type];\n if (!paneKind && definition.paneClass && dom.hasClass(node, definition.paneClass)) {\n paneKind = definition.paneKind;\n }\n });\n if (paneKind) { return paneKind; }\n\n if (dom.hasClass(node, 'ge-tab')) { return 'tab'; }\n if (dom.hasClass(node, 'ge-accordion-item')) { return 'accordion-item'; }\n if (dom.hasClass(node, 'row')) { return 'row'; }\n if (dom.hasClass(node, 'column')) { return 'column'; }\n if (dom.hasClass(node, 'ge-element')) { return 'element'; }\n // A content area is a text when an editor's type is on it, and the\n // host's plain content when there is none\n if (dom.hasClass(node, 'ge-text-block')) { node = dom.child(node, '.ge-content') || node; }\n if (dom.hasClass(node, 'ge-content')) { return node.getAttribute('data-ge-content-type') ? 'text' : 'plain'; }\n return 'node';\n }\n\n // Copy html to sourceElement if a source textarea is given\n if (settings.source_textarea) {\n var sourceHtml = nodeFrom(settings.source_textarea).value;\n // Html with no grid in it goes into a row and a full width column\n // of its own, where init wraps it as the host's plain content\n var probe = dom.element('div');\n probe.innerHTML = sourceHtml;\n if (sourceHtml.length > 0 && !probe.querySelector('.row')) {\n sourceHtml = '<div class=\"row\"><div class=\"col-lg-12\">' + sourceHtml + '</div></div>';\n }\n dom.setHtml(baseElem, sourceHtml);\n }\n\n // Wrap content if it is non-bootstrap\n if (baseElem.children.length && !baseElem.querySelector('div.row')) {\n var children = dom.children(baseElem);\n var newRow = dom.create('<div class=\"row\"><div class=\"col-lg-12\"></div></div>');\n baseElem.appendChild(newRow);\n children.forEach(function(child) { newRow.firstChild.appendChild(child); });\n }\n\n // setup() and init() run at the end of this function, once every\n // table and helper below has been assigned: the toolbar is built from\n // the container registry, and a var declared later is not there yet.\n\n function setup() {\n htmlTextArea = dom.element('textarea', { 'class': 'ge-html-output' });\n canvas.parentNode.insertBefore(htmlTextArea, canvas);\n\n createMainControls();\n watchDrawers();\n\n var signal = { signal: lifetime.signal };\n\n // Make controls fixed on scroll\n window.addEventListener('scroll', onScroll, signal);\n\n /* A click on the host's plain content offers to make it a text */\n dom.delegate(canvas, 'click', '.ge-content', onContentClick, signal);\n\n /* A trigger is often a link, and a link still navigates even\n with its Bootstrap attributes suspended */\n dom.delegate(canvas, 'click', '.ge-popup-trigger, [data-ge-popup-target]', function(e) {\n if (dom.hasClass(canvas, 'ge-editing')) { e.preventDefault(); }\n }, signal);\n\n if (settings.active_target) {\n // Whatever the click was for - a text, a tool - it also says\n // where the toolbar adds next. A click on no column or region\n // says nowhere, and the toolbar adds to the canvas again.\n // The click a drag ends in - a resize, a move - is not one:\n // it comes where the pointer let go, not where it pressed\n var pressed = null;\n canvas.addEventListener('pointerdown', function(e) {\n pressed = { x: e.clientX, y: e.clientY };\n }, signal);\n canvas.addEventListener('click', function(e) {\n var from = pressed;\n pressed = null;\n if (!dom.hasClass(canvas, 'ge-editing')) { return; }\n if (from && Math.abs(e.clientX - from.x) + Math.abs(e.clientY - from.y) > settings.drag.threshold) { return; }\n var region = dom.closest(e.target, targetSelector());\n\n // The target's own background, or its drawer's, clicked\n // again takes it back. What is in it - a text, a tool, a\n // nested column - keeps it, or makes that the target\n if (region && region === activeTarget &&\n (e.target === region || e.target === dom.child(region, '.ge-tools-drawer'))) {\n changeTarget(null);\n return;\n }\n\n changeTarget(region && region !== canvas && canvas.contains(region) ? region : null);\n }, signal);\n\n // Escape is the panel's, the dialog's, and a field's or a\n // text's while one has the focus; after those, it is this\n document.addEventListener('keydown', function(e) {\n if (e.key !== 'Escape' || !activeTarget || openSettingsState || dialogState) { return; }\n var focus = document.activeElement;\n if (focus && (dom.is(focus, 'input, textarea, select') || focus.isContentEditable)) { return; }\n changeTarget(null);\n }, signal);\n }\n }\n\n /**\n * A rich text editor rewrites the content area as it takes over,\n * which costs the element drawers inside it. The integrations say\n * when their editor is ready, and the drawers go back in.\n */\n function textReady(block) {\n if (!dom.is(block, '.ge-content') || !canvas.contains(block)) { return; }\n\n plugins('onContentReady', block);\n refreshPreviews(block);\n }\n\n /**\n * The toolbar above the canvas. Separate from setup() because every\n * string in it comes from the locale, so setLocale() rebuilds it.\n */\n function createMainControls() {\n mainControls = dom.element('div', { 'class': 'ge-mainControls' });\n htmlTextArea.parentNode.insertBefore(mainControls, htmlTextArea);\n wrapper = mainControls.appendChild(dom.element('div', { 'class': 'ge-wrapper ge-top' }));\n\n // With the overflow menu, the add buttons stand in a line of\n // their own that keeps to one line, beside the menu's button\n var overflowMenu = settings.toolbar_overflow !== 'wrap';\n var start = wrapper;\n if (overflowMenu) {\n dom.addClass(wrapper, 'ge-toolbar-menu');\n start = wrapper.appendChild(dom.element('div', { 'class': 'ge-toolbar-start' }));\n }\n\n addButtons = [];\n\n // Add row\n addRowGroup = start.appendChild(dom.element('div', { 'class': 'ge-addRowGroup btn-group' }));\n addContainerGroup = dom.element('div', { 'class': 'ge-addContainerGroup btn-group ms-1' });\n settings.new_row_layouts.forEach(function(layout) {\n var grouped = !Array.isArray(layout);\n var btn = dom.element('a', {\n 'class': 'btn btn-sm btn-light',\n title: grouped\n ? t('row.add_row_cols', { columns: layout.columns, counts: rowColsText(layout.row_cols) })\n : t('row.add', { layout: layout.join('-') }),\n // What this button makes, in the markup rather than in\n // memory: a drag works on a clone of it\n 'data-ge-toolbar': 'row',\n 'data-ge-layout': grouped ? JSON.stringify(layout) : layout.join(','),\n });\n\n btn.addEventListener('click', function() {\n if (activeTarget) { addToTarget(btn, 'tool'); return; }\n\n var row = rowFromLayoutValue(layout);\n\n var added = addNode('row', row, function() {\n canvas.appendChild(row);\n }, { parent: canvas, source: 'tool' });\n\n if (added && row.scrollIntoView) {\n row.scrollIntoView({behavior: 'smooth'});\n }\n });\n addRowGroup.appendChild(btn);\n addButtons.push({ button: btn, home: addRowGroup, group: 'rows' });\n\n btn.appendChild(dom.create('<i class=\"bi bi-plus\"></i>'));\n\n // A row of columns shares out the icon as they share the row;\n // a row with row-cols draws one line of its widest count\n var sizes = grouped ? rowColsIcon(layout) : layout;\n var icon = '<div class=\"row ge-row-icon\">';\n sizes.forEach(function(size) {\n icon += '<div class=\"column ' + sizeClass(BREAKPOINTS[0], size) + '\"></div>';\n });\n icon += '</div>';\n btn.appendChild(dom.create(icon));\n });\n\n start.appendChild(addContainerGroup);\n\n // A container starts in a row of its own, the way the add row\n // buttons next to these ones do\n Object.keys(CONTAINERS).forEach(function(type) {\n var definition = CONTAINERS[type];\n var button = labelButton(dom.element('a', { 'class': 'btn btn-sm btn-light ge-add-container' }),\n t(definition.labelKey), definition.iconClass);\n\n dom.attr(button, { 'data-ge-toolbar': 'container', 'data-ge-container-type': type });\n button.addEventListener('click', function() {\n if (activeTarget) { addToTarget(button, 'tool'); return; }\n\n var row = createRow();\n var column = row.appendChild(createColumn(MAX_COL_SIZE));\n var container = column.appendChild(definition.create({}));\n\n addNode(type, container, function() {\n canvas.appendChild(row);\n }, { parent: canvas, source: 'tool' });\n });\n addContainerGroup.appendChild(button);\n addButtons.push({ button: button, home: addContainerGroup, group: toolbarGroupOf(definition.group) || 'content' });\n });\n\n // A feature plugin's own buttons, beside the containers': what\n // one makes goes onto the canvas, where the plugin says it belongs.\n // One with align 'end' goes on the right instead, as an icon,\n // beside the source and preview buttons.\n var endItems = [];\n shownToolbar = {};\n Object.keys(FEATURES).forEach(function(name) {\n shownToolbar[name] = toolbarOf(FEATURES[name]);\n shownToolbar[name].forEach(function(item, index) {\n var button = featureButton(name, item, index);\n\n if (item.align === 'end') {\n endItems.push(button);\n } else {\n addContainerGroup.appendChild(button);\n // One that names no category of its own has its plugin's\n addButtons.push({ button: button, home: addContainerGroup, group: toolbarGroupOf(item.group) || name });\n }\n });\n });\n\n // Buttons on right\n layoutDropdown = dom.create('<div class=\"dropdown pull-right ge-layout-mode\">' +\n '<button type=\"button\" class=\"btn btn-sm btn-primary dropdown-toggle\" data-bs-toggle=\"dropdown\"></button>' +\n '<div class=\"dropdown-menu\" role=\"menu\"></div>' +\n '</div>');\n dom.delegate(layoutDropdown, 'click', 'a', function() {\n // Through changeView, so the dropdown and the method are\n // one path rather than two that have to agree\n changeView(this.getAttribute('data-ge-view'));\n });\n wrapper.appendChild(layoutDropdown);\n\n settings.layout_modes.forEach(function(view) {\n dom.one(layoutDropdown, '.dropdown-menu').appendChild(dom.element('a', {\n 'class': 'dropdown-item',\n 'data-ge-view': view,\n title: t(labelKeyFor(view)),\n }, t(labelKeyFor(view))));\n });\n dom.one(layoutDropdown, 'button').textContent = t(labelKeyFor(curView));\n\n var btnGroup = wrapper.appendChild(dom.element('div', { 'class': 'btn-group pull-right' }));\n\n if (settings.edit_source) {\n // Built again by setLocale, maybe with the source open\n var htmlButton = dom.create('<button type=\"button\" class=\"btn btn-sm btn-primary gm-edit-mode\"><i class=\"bi bi-code-slash\"></i></button>');\n htmlButton.setAttribute('title', t('tool.edit_source'));\n dom.toggleClass(htmlButton, 'active btn-danger', sourceOpen);\n htmlButton.addEventListener('click', function() {\n if (sourceOpen) {\n closeSource();\n } else {\n openSource();\n }\n\n dom.toggleClass(htmlButton, 'active btn-danger', sourceOpen);\n });\n btnGroup.appendChild(htmlButton);\n }\n\n var previewButton = dom.create('<button type=\"button\" class=\"btn btn-sm btn-primary gm-preview\"><i class=\"bi bi-eye-fill\"></i></button>');\n var endPreview = function() {\n if (!dom.hasClass(previewButton, 'active')) {\n dom.addClass(canvas, 'ge-editing');\n }\n };\n previewButton.setAttribute('title', t('tool.preview'));\n previewButton.addEventListener('mouseenter', function() {\n dom.removeClass(canvas, 'ge-editing');\n });\n previewButton.addEventListener('click', function() {\n dom.toggleClass(previewButton, 'active btn-danger');\n endPreview();\n });\n previewButton.addEventListener('mouseleave', endPreview);\n btnGroup.appendChild(previewButton);\n\n // Floated right after the source and preview buttons, so it\n // stands to their left. Not a btn-group: its buttons show one at\n // a time, and a hidden one still counts as a neighbour to\n // Bootstrap, which squares off the corners they would share.\n if (endItems.length) {\n var end = wrapper.appendChild(dom.element('div', { 'class': 'pull-right ge-toolbar-end' }));\n endItems.forEach(function(button) { end.appendChild(button); });\n }\n\n if (settings.toolbar_groups) { createGroupTabs(start); }\n if (overflowMenu) { createOverflowMenu(start); }\n\n makeToolbarDraggable();\n }\n\n /** The core's categories, ahead of the plugins' own. */\n var CORE_GROUPS = [\n { name: 'rows', labelKey: 'group.rows' },\n { name: 'content', labelKey: 'group.content' },\n { name: 'elements', labelKey: 'group.elements' },\n ];\n\n /** A plugin's category, when it names one. */\n function toolbarGroupOf(value) {\n return typeof value === 'string' && value.trim() !== '' ? value : null;\n }\n\n /**\n * toolbar_groups: tabs at the start of the toolbar, one per category\n * of add buttons, and only the chosen one's buttons on it. The rest\n * wait in a hidden stash inside the toolbar, so toolbarItems still\n * finds them and the btn-groups round the corners of what shows. With\n * a single category there is nothing to choose, and no tabs.\n */\n function createGroupTabs(start) {\n // The core's two first, then the rest as their first button comes\n var names = CORE_GROUPS.map(function(group) { return group.name; });\n addButtons.forEach(function(entry) {\n if (names.indexOf(entry.group) < 0) { names.push(entry.group); }\n });\n names = names.filter(function(name) {\n return addButtons.some(function(entry) { return entry.group === name; });\n });\n\n if (names.length < 2) { return; }\n\n var tabs = dom.element('div', { 'class': 'ge-toolbar-groups btn-group', role: 'tablist', 'aria-label': t('group.select') });\n start.insertBefore(tabs, start.firstChild);\n var stash = mainControls.appendChild(dom.element('div', { 'class': 'ge-toolbar-stash', hidden: 'hidden' }));\n\n names.forEach(function(name) {\n var tab = tabs.appendChild(dom.element('button', {\n type: 'button',\n 'class': 'btn btn-sm btn-outline-secondary',\n role: 'tab',\n 'data-ge-group': name,\n }, groupLabel(name)));\n\n tab.addEventListener('click', function() { showGroup(name); });\n });\n\n showGroup(names.indexOf(toolbarGroup) >= 0 ? toolbarGroup : names[0]);\n\n function showGroup(name) {\n toolbarGroup = name;\n\n addButtons.forEach(function(entry) {\n (entry.group === name ? entry.home : stash).appendChild(entry.button);\n });\n\n dom.children(tabs).forEach(function(tab) {\n var chosen = tab.getAttribute('data-ge-group') === name;\n dom.toggleClass(tab, 'active', chosen);\n tab.setAttribute('aria-selected', chosen ? 'true' : 'false');\n });\n\n refitToolbar();\n }\n }\n\n /** A category's label: its group.<name> string, or its first button's when it has none. */\n function groupLabel(name) {\n var key = 'group.' + name;\n if (hasString(settings, key)) { return t(key); }\n\n var first = addButtons.filter(function(entry) { return entry.group === name; })[0];\n return first.button.getAttribute('title') || name;\n }\n\n /** The add buttons on the toolbar's line: all of them, or the chosen category's. */\n function shownAddButtons() {\n return addButtons.filter(function(entry) { return !dom.closest(entry.button, '.ge-toolbar-stash'); });\n }\n\n /** The toolbar off the page, with what keeps its overflow menu up to date. */\n /** A feature plugin's toolbar items: its array, or what its function returns now. */\n function toolbarOf(feature) {\n var items = typeof feature.toolbar === 'function' ? feature.toolbar() : feature.toolbar;\n return Array.isArray(items) ? items : [];\n }\n\n /**\n * ge.refreshToolbar(): the toolbar built again, from what the plugins'\n * toolbars hold now - a plugin whose buttons come and go calls it when\n * they have. The category shown, the preview and the source view stay\n * as they are; an open overflow menu folds away.\n */\n function refreshToolbar() {\n // Not built yet - the first one reads the toolbars as they are\n // then - or taken away for good\n if (!mainControls || destroyed) { return; }\n\n var previewing = !!dom.one(mainControls, '.gm-preview.active');\n\n removeMainControls();\n createMainControls();\n\n if (previewing) {\n dom.addClass(dom.one(mainControls, '.gm-preview'), 'active btn-danger');\n }\n onScroll();\n }\n\n function removeMainControls() {\n if (toolbarLifetime) { toolbarLifetime.abort(); }\n toolbarLifetime = null;\n closeOverflowMenu = function() {};\n refitToolbar = function() {};\n mainControls.remove();\n }\n\n /**\n * The add buttons that don't fit on the toolbar's line, behind a\n * button at its end. They are the same buttons, moved rather than\n * copied, so a click, a drag or a plugin finding them with\n * toolbarItems works as it does on the line. Which ones go is worked\n * out again whenever the toolbar or what is on it changes size.\n */\n function createOverflowMenu(start) {\n var more = dom.create('<div class=\"ge-toolbar-more\">' +\n '<button type=\"button\" class=\"btn btn-sm btn-light\"><i class=\"bi bi-three-dots\"></i></button>' +\n '<div class=\"ge-toolbar-overflow\">' +\n '<div class=\"ge-addRowGroup btn-group\"></div>' +\n '<div class=\"ge-addContainerGroup btn-group\"></div>' +\n '</div>' +\n '</div>');\n start.parentNode.insertBefore(more, start.nextSibling);\n\n var toggle = dom.one(more, 'button');\n var panel = dom.one(more, '.ge-toolbar-overflow');\n var spares = dom.all(panel, '.btn-group');\n // The spare group in the menu for each group on the line\n function spareOf(home) {\n return home === addRowGroup ? spares[0] : spares[1];\n }\n\n toggle.setAttribute('title', t('tool.more'));\n toggle.setAttribute('aria-haspopup', 'true');\n toggle.setAttribute('aria-expanded', 'false');\n\n var menuLifetime = toolbarLifetime = new AbortController();\n var signal = { signal: menuLifetime.signal };\n\n toggle.addEventListener('click', function() { openOverflow(!dom.hasClass(more, 'ge-open')); });\n // A button in the menu has done its job once it is clicked\n panel.addEventListener('click', function(e) {\n if (dom.closest(e.target, '[data-ge-toolbar]')) { openOverflow(false); }\n });\n document.addEventListener('pointerdown', function(e) {\n if (!more.contains(e.target)) { openOverflow(false); }\n }, signal);\n document.addEventListener('keydown', function(e) {\n if (e.key === 'Escape') { openOverflow(false); }\n }, signal);\n closeOverflowMenu = function() { openOverflow(false); };\n // A category chosen: another set of buttons to fit\n refitToolbar = fit;\n\n fit();\n\n if (window.ResizeObserver) {\n // Not in the callback itself: moving buttons there would\n // resize what is being observed before the frame is drawn\n var pending = false;\n var observer = new window.ResizeObserver(function() {\n if (pending) { return; }\n pending = true;\n window.requestAnimationFrame(function() {\n pending = false;\n if (!menuLifetime.signal.aborted) { fit(); }\n });\n });\n // The toolbar's width, and the buttons on the right of it\n // showing and hiding, as the paste button does\n observer.observe(wrapper);\n observer.observe(start);\n menuLifetime.signal.addEventListener('abort', function() { observer.disconnect(); });\n }\n\n function openOverflow(open) {\n open = open && dom.hasClass(more, 'ge-needed');\n dom.toggleClass(more, 'ge-open', open);\n toggle.setAttribute('aria-expanded', open ? 'true' : 'false');\n }\n\n /** Back on the line, then the last ones off it until the rest fit. */\n function fit() {\n // Only the chosen category's, with toolbar_groups: the others\n // wait in their stash\n var homes = shownAddButtons();\n homes.forEach(function(entry) { entry.home.appendChild(entry.button); });\n dom.removeClass(more, 'ge-needed');\n\n if (start.scrollWidth <= start.clientWidth) {\n openOverflow(false);\n return;\n }\n\n dom.addClass(more, 'ge-needed');\n for (var i = homes.length - 1; i >= 0 && start.scrollWidth > start.clientWidth; i--) {\n var into = spareOf(homes[i].home);\n into.insertBefore(homes[i].button, into.firstChild);\n }\n }\n }\n\n /**\n * A toolbar button's face: the plugin's icon alone when it has one,\n * with its label as the title, or a plus and the label otherwise.\n */\n function labelButton(button, label, iconClass) {\n button.setAttribute('title', label);\n\n if (iconClass) {\n button.appendChild(dom.element('i', { 'class': iconClass }));\n return button;\n }\n\n button.appendChild(dom.create('<i class=\"bi bi-plus\"></i>'));\n button.appendChild(dom.element('span', {}, label));\n return button;\n }\n\n /** A feature plugin's toolbar button. At the end it is always an icon, `bi bi-plus` if it has none of its own. */\n function featureButton(name, item, index) {\n var iconClass = item.iconClass || (item.align === 'end' ? 'bi bi-plus' : null);\n // A label of its own, worked out when the toolbar is built - and\n // built again by setLocale - or the string its labelKey names\n var label = typeof item.label === 'function' ? item.label() : (item.label || t(item.labelKey));\n // Grey with the add buttons on the left, blue with the source and\n // preview buttons on the right\n var colour = item.align === 'end' ? 'btn-primary' : 'btn-light';\n var button = labelButton(dom.element('a', { 'class': 'btn btn-sm ' + colour + ' ge-add-container ge-add-feature' }), label, iconClass);\n\n dom.addClass(button, item.className || '');\n dom.attr(button, {\n 'data-ge-toolbar': 'feature',\n 'data-ge-feature': name,\n 'data-ge-item': index,\n });\n button.addEventListener('click', function() {\n if (activeTarget) { addToTarget(button, item.source || 'tool'); return; }\n\n var made = item.create();\n // A plugin that could not make one says so with null\n if (!made) { return; }\n\n // One that belongs in a column brings a row and a column\n // of its own, the way a container does\n var placed = item.inColumn ? inRowOfItsOwn(made) : made;\n\n var added = addNode(item.kind, made, function() {\n canvas.appendChild(placed);\n }, { parent: canvas, source: item.source || 'tool' });\n\n if (added && item.inColumn && placed.scrollIntoView) {\n placed.scrollIntoView({behavior: 'smooth'});\n }\n });\n\n return button;\n }\n\n /**\n * The toolbar's buttons as a palette: drag one onto the canvas and\n * what it makes is created where it lands, rather than at the end.\n *\n * On by default in the mode where everything else is dragged by its\n * body rather than by a handle, since that is the same idea applied to\n * the toolbar; toolbar_drag: true or false decides it outright.\n */\n function toolbarDrags() {\n if (settings.toolbar_drag === 'auto') { return settings.drag_handle === 'drawer'; }\n\n return !!settings.toolbar_drag;\n }\n\n function makeToolbarDraggable() {\n var buttons = dom.all(mainControls, '[data-ge-toolbar]');\n\n buttons.forEach(function(button) {\n dom.removeClass(button, 'ge-palette-button');\n button.removeEventListener('pointerdown', startToolbarDrag);\n });\n\n if (!toolbarDrags()) { return; }\n\n buttons.forEach(function(button) {\n dom.addClass(button, 'ge-palette-button');\n button.addEventListener('pointerdown', startToolbarDrag);\n });\n }\n\n /**\n * A toolbar button carried onto the canvas.\n *\n * Nothing happens until the pointer has moved far enough to mean it:\n * below that the gesture is a click, and the button's own handler\n * adds the block at the end of the canvas as it always has - which is\n * also what keeps the add column tool's hold-to-pick working.\n */\n function startToolbarDrag(e) {\n var button = e.currentTarget;\n var startX = e.pageX;\n var startY = e.pageY;\n var helper = null;\n\n if (e.button) { return; }\n\n function far(move) {\n return Math.abs(move.pageX - startX) + Math.abs(move.pageY - startY) >\n settings.drag.threshold;\n }\n\n function onMove(move) {\n if (!helper) {\n if (!far(move)) { return; }\n\n helper = dom.addClass(button.cloneNode(true), 'ge-toolbar-helper');\n document.body.appendChild(helper);\n // The menu a button came from would hide where it lands\n closeOverflowMenu();\n dom.addClass(canvas, 'ge-dropping');\n }\n\n dom.css(helper, { left: move.pageX - 14, top: move.pageY - 14 });\n showDropMarker(move.pageX, move.pageY);\n }\n\n function onUp(up) {\n document.removeEventListener('pointermove', onMove);\n dom.off(document, 'pointerup pointercancel', onUp);\n\n if (!helper) { return; }\n\n helper.remove();\n dom.removeClass(canvas, 'ge-dropping');\n hideDropMarker();\n\n // The click that follows a drag would add the block a second\n // time, at the end of the canvas. Caught on the way down, so\n // it never reaches the button's own handler.\n var swallow = function(click) {\n if (click.target !== button && !button.contains(click.target)) { return; }\n click.preventDefault();\n click.stopImmediatePropagation();\n };\n window.addEventListener('click', swallow, { capture: true, once: true });\n // A drag the browser does not follow with a click leaves\n // nothing to swallow: the next click is a click\n window.setTimeout(function() { window.removeEventListener('click', swallow, { capture: true }); }, 0);\n\n var where = dropPlaceAt(up.pageX, up.pageY);\n if (where) { insertFromToolbar(button, where); }\n }\n\n // On the document, not on the button: until the gesture is far\n // enough along to be a drag there is nothing to capture the\n // pointer with, and the pointer has left the button by then\n document.addEventListener('pointermove', onMove);\n dom.on(document, 'pointerup pointercancel', onUp);\n }\n\n /**\n * Where a drop at this point would put things: which region it lands\n * in, and which of that region's children it goes before.\n *\n * Worked out from the pointer rather than handed to a sortable. The\n * canvas is a tree of regions that connected sortables fight over -\n * a column grows as a placeholder is put in it, until it covers the\n * pointer wherever the pointer goes - and a new block has one\n * question to answer, which is where it lands.\n */\n function dropPlaceAt(pageX, pageY) {\n var x = pageX - window.scrollX;\n var y = pageY - window.scrollY;\n var under = document.elementFromPoint(x, y);\n\n if (!under) { return null; }\n\n var region = dom.closest(under, ['.column', '.ge-canvas'].concat(pluginHooks('regions')).join(', '));\n if (!region || (region !== canvas && !canvas.contains(region))) {\n return null;\n }\n\n var before = null;\n\n dom.children(region, blockSelector()).forEach(function(block) {\n if (before) { return; }\n\n var box = block.getBoundingClientRect();\n if (y < box.top + box.height / 2) { before = block; }\n });\n\n return { region: region, before: before };\n }\n\n /**\n * A feature's toolbar button dropped on the canvas. A region that will\n * not have what it makes - a section dropped on a column - gives way\n * to the canvas, just after the top level block the pointer was in.\n */\n function insertFeatureFromToolbar(button, where, source) {\n // The item the button was built from, whatever the plugin's list\n // says now: it may have changed since, and the toolbar not yet\n var item = (shownToolbar[button.getAttribute('data-ge-feature')] || [])[parseInt(button.getAttribute('data-ge-item'), 10)];\n if (!item) { return null; }\n var made = item.create();\n if (!made) { return null; }\n var placed = made;\n\n if (item.inColumn) {\n // Where it lands in a column, or in a row and a column of its\n // own anywhere else\n if (!dom.is(where.region, '.column')) { placed = inRowOfItsOwn(made); }\n } else if (!acceptsBlock(where.region, made)) {\n var ancestors = where.region === canvas ? [] : dom.parentsUntil(where.region, canvas).reverse().concat([where.region]);\n var top = ancestors[0] || null;\n where = { region: canvas, before: top ? top.nextElementSibling : null };\n }\n\n return addNode(item.kind, made, function() {\n if (where.before) {\n where.before.parentNode.insertBefore(placed, where.before);\n } else {\n where.region.appendChild(placed);\n }\n }, { parent: where.region, source: item.source || source || 'dragdrop' });\n }\n\n /** A detached row with one full width column holding `node`. */\n function inRowOfItsOwn(node) {\n var row = createRow();\n row.appendChild(createColumn(MAX_COL_SIZE)).appendChild(node);\n\n return row;\n }\n\n /** A line where the block would go, following the pointer. */\n function showDropMarker(pageX, pageY) {\n var where = dropPlaceAt(pageX, pageY);\n\n if (!where) { return hideDropMarker(); }\n\n if (!dropMarker) { dropMarker = dom.element('div', { 'class': 'ge-drop-marker' }); }\n\n if (where.before) {\n where.before.parentNode.insertBefore(dropMarker, where.before);\n } else {\n where.region.appendChild(dropMarker);\n }\n\n return undefined;\n }\n\n function hideDropMarker() {\n if (dropMarker) { dropMarker.remove(); }\n }\n\n /**\n * The row or container a toolbar button stands for, made and put where\n * the pointer left it.\n */\n function insertFromToolbar(button, where, source) {\n if (button.getAttribute('data-ge-toolbar') === 'feature') {\n return insertFeatureFromToolbar(button, where, source);\n }\n\n var container = button.getAttribute('data-ge-toolbar') === 'container';\n var type = button.getAttribute('data-ge-container-type');\n var made = container\n ? CONTAINERS[type].create({})\n : rowFromLayout(button.getAttribute('data-ge-layout'));\n\n // A container belongs in a column: dropped straight onto the\n // canvas it brings a row and a column of its own\n var placed = made;\n if (container && !dom.is(where.region, '.column')) { placed = inRowOfItsOwn(made); }\n\n return addNode(container ? type : 'row', made, function() {\n if (where.before) {\n where.before.parentNode.insertBefore(placed, where.before);\n } else {\n where.region.appendChild(placed);\n }\n }, { parent: where.region, source: source || 'dragdrop' });\n }\n\n /**\n * The column width as a utility family, so the Responsive section of\n * a column's panel has a field for it: every size, units or not, in\n * the view being edited. A write is a resize, through the resize\n * events, not a utility change.\n */\n function widthFamily() {\n var values = [];\n for (var units = 1; units <= MAX_COL_SIZE; units++) { values.push(String(units)); }\n\n return {\n name: 'col',\n values: values.concat(FLEX_SIZES),\n appliesTo: ['column'],\n labelKey: 'utility.col_width',\n className: function(key, value) { return sizeClass(breakpoint(key), parseSize(value)); },\n choices: function() { return settings.valid_col_sizes.map(String); },\n label: function(value) {\n if (value === 'equal') { return t('utility.col_equal'); }\n if (value === 'auto') { return t('utility.col_auto'); }\n\n return value;\n },\n write: function(col, value, view, source) {\n return resizeColumn(col, value === null ? null : parseSize(value), source, view);\n },\n // With no size of its own, a column in a row with row-cols\n // takes its share from the row, which the field says\n blank: function(col, view) {\n var winner = view === ALL_VIEW ? null : rowColsWinner(col, breakpoint(view));\n return winner ? t('utility.col_from_row', { count: rowColsLabel(winner.value) }) : null;\n },\n };\n }\n\n /** A size as markup or a select carries it: '4' is 4, 'equal' and 'auto' are themselves. */\n function parseSize(size) {\n return /^\\d+$/.test(String(size)) ? parseInt(size, 10) : size;\n }\n\n /** A row from a toolbar button's data-ge-layout: sizes, or a row-cols layout as JSON. */\n function rowFromLayout(layout) {\n if (/^\\s*\\{/.test(layout || '')) { return rowFromLayoutValue(JSON.parse(layout)); }\n\n return rowFromLayoutValue((layout || '').split(',').filter(function(size) {\n return size !== '';\n }).map(parseSize));\n }\n\n /**\n * A row from a layout: an array of sizes, or { row_cols, columns } -\n * row-cols per breakpoint, and that many columns sized by the row.\n */\n function rowFromLayoutValue(layout) {\n var row = createRow();\n\n if (Array.isArray(layout)) {\n layout.forEach(function(size) { row.appendChild(createColumn(size)); });\n return row;\n }\n\n Object.keys(layout.row_cols || {}).forEach(function(key) {\n var value = layout.row_cols[key];\n var tier = breakpoint(key);\n if (tier && ROW_COLS_VALUES.indexOf(String(value)) !== -1) { dom.addClass(row, rowColsClass(tier, value)); }\n });\n\n for (var i = 0; i < (layout.columns || 0); i++) { row.appendChild(createColumn(null)); }\n\n return row;\n }\n\n /** \"1, md: 3\": a row-cols layout's counts, for its button's title. */\n function rowColsText(counts) {\n return BREAKPOINTS.filter(function(tier) { return counts && counts[tier.key] !== undefined; })\n .map(function(tier) { return (tier.infix ? tier.key + ': ' : '') + counts[tier.key]; })\n .join(', ');\n }\n\n /** The icon of a row-cols layout: one line of equal columns, as many as its widest count. */\n function rowColsIcon(layout) {\n var widest = 1;\n Object.keys(layout.row_cols || {}).forEach(function(key) {\n var value = layout.row_cols[key];\n if (value !== 'auto') { widest = Math.max(widest, parseInt(value, 10) || 1); }\n });\n\n return Array.apply(null, Array(Math.min(widest, layout.columns || widest))).map(function() { return 'equal'; });\n }\n\n function onScroll() {\n var scrollTop = window.pageYOffset;\n\n if (\n scrollTop > dom.offset(mainControls).top &&\n scrollTop < dom.offset(canvas).top + dom.contentHeight(canvas)\n ) {\n if (dom.hasClass(wrapper, 'ge-top')) {\n dom.css(wrapper, {\n left: dom.offset(wrapper).left,\n width: dom.outerWidth(wrapper),\n });\n dom.removeClass(wrapper, 'ge-top');\n dom.addClass(wrapper, 'ge-fixed');\n }\n } else {\n if (dom.hasClass(wrapper, 'ge-fixed')) {\n dom.css(wrapper, { left: '', width: '' });\n dom.removeClass(wrapper, 'ge-fixed');\n dom.addClass(wrapper, 'ge-top');\n }\n }\n }\n\n /**\n * A click on the host's plain content makes it a text: of the one\n * editor offered, or of the one chosen when there are several. What\n * a click on a text does is its editor plugin's business.\n */\n function onContentClick() {\n var block = this;\n if (block.getAttribute('data-ge-content-type')) { return; }\n\n // A second click, with the choice still open, withdraws it\n if (closeSizePicker()) { return; }\n\n // Content nobody can see - a tab that is not the open one, a\n // closed accordion item - has no geometry for an editor to lay\n // its toolbar out against, and nothing anyone can type into\n if (!dom.visible(block)) { return; }\n\n var offers = textOffers();\n if (!offers.length) { return; }\n\n if (offers.length === 1) {\n convertPlain(block, offers[0]);\n } else {\n openConvertPicker(block, offers);\n }\n }\n\n /**\n * Plain content made a text of `offer`'s type, through the convert\n * events: the type goes on, and the plugin that declared it takes the\n * block over and opens its editor. Nothing else about the node\n * changes. False when the library is missing or a handler canceled.\n */\n function convertPlain(block, offer) {\n // Not converted, so the next click tries again: the library may\n // be loaded by then\n if (offer.available && !offer.available()) {\n if (offer.missingKey) { console.error(t(offer.missingKey)); }\n return false;\n }\n\n return operate(function() {\n var payload = payloadFor('plain', block, { source: 'tool', from: 'plain', to: offer.type });\n\n if (!emit('before-convert', payload)) { return false; }\n\n dom.addClass(block, 'ge-content-type-' + offer.type);\n block.setAttribute('data-ge-content-type', offer.type);\n\n // Its plain drawer goes: the block is the plugin's now, and\n // the plugin gives it the drawer a text has\n var textBlock = block.parentElement;\n if (dom.hasClass(textBlock, 'ge-text-block')) {\n dom.removeClass(textBlock, 'ge-plain-block');\n dom.children(textBlock, '.ge-tools-drawer').forEach(function(drawer) { drawer.remove(); });\n }\n\n emit('after-convert', payload);\n offer.edit(block);\n\n return true;\n });\n }\n\n /**\n * The text types offered, as a strip under the plain content's\n * drawer, when there is more than one to choose from.\n */\n function openConvertPicker(block, offers) {\n var textBlock = dom.hasClass(block.parentElement, 'ge-text-block') ? block.parentElement : null;\n if (!textBlock) { return; }\n\n openPicker(dom.child(textBlock, '.ge-tools-drawer'), offers.map(function(offer) {\n return {\n label: offer.label,\n title: t('tool.convert_type', { editor: offer.label }),\n attributes: { 'data-ge-content-type': offer.type },\n choose: function() { convertPlain(block, offer); },\n };\n }), 'ge-text-picker ge-convert-picker', textBlock);\n }\n\n /**\n * A choice as a strip under `anchor` - a tool, or a drawer - one\n * button per `{ label, title, attributes, choose }`. Leaving `hover`\n * (the anchor by default) withdraws it, and so does closeSizePicker.\n */\n function openPicker(anchor, choices, className, hover) {\n closeSizePicker();\n if (!anchor) { return; }\n\n var drawer = dom.closest(anchor, '.ge-tools-drawer');\n if (drawer) { dom.addClass(drawer, 'ge-picker-open'); }\n sizePicker = anchor.appendChild(dom.addClass(dom.element('div', { 'class': 'ge-size-picker' }), className || ''));\n\n choices.forEach(function(choice) {\n var button = dom.attr(dom.element('a', { 'class': 'ge-size ge-size-flex' }), choice.attributes || {});\n\n button.setAttribute('title', choice.title || choice.label);\n button.textContent = choice.label;\n button.addEventListener('click', function(e) {\n e.preventDefault();\n e.stopPropagation();\n\n closeSizePicker();\n choice.choose();\n });\n sizePicker.appendChild(button);\n });\n\n withdrawOnLeave(hover || anchor);\n }\n\n /** Leaving `node` withdraws the picker open under it, unless the pointer went into the picker. */\n function withdrawOnLeave(node) {\n node.addEventListener('mouseleave', function() {\n window.setTimeout(function() {\n if (sizePicker && !sizePicker.matches(':hover')) { closeSizePicker(); }\n }, 400);\n }, { once: true });\n }\n\n /**\n * Every text type the feature plugins declare, in the order they\n * were registered: the first plugin to declare a type owns it.\n */\n function textTypes() {\n var owners = {};\n var entries = [];\n\n Object.keys(FEATURES).forEach(function(name) {\n var feature = FEATURES[name];\n if (!feature.textTypes) { return; }\n\n (feature.textTypes() || []).forEach(function(entry) {\n if (owners[entry.type]) {\n if (owners[entry.type] !== name) {\n warnOnceHere('text-type:' + entry.type, 'the \"' + name + '\" plugin declares the ' +\n 'text type \"' + entry.type + '\", which the \"' + owners[entry.type] +\n '\" plugin already declares: ignored');\n }\n return;\n }\n\n owners[entry.type] = name;\n entries.push(entry);\n });\n });\n\n return entries;\n }\n\n /** The types plain content can be made, in order: the ones not marked `offered: false`. */\n function textOffers() {\n return textTypes().filter(function(entry) { return entry.offered !== false; });\n }\n\n /** Whether a plugin declares this text type. */\n function hasTextOwner(type) {\n return textTypes().some(function(entry) { return entry.type === type; });\n }\n\n function reset() {\n deinit();\n init();\n }\n\n /**\n * The canvas as html, in the textarea in its place, to edit by hand.\n * A feature plugin's onSourceOpen may put a code editor over the\n * textarea; its onSourceClose puts what it holds back in it, which is\n * what the canvas is made of again.\n */\n function openSource() {\n deinit();\n // The canvas is made again from the html when it comes back\n changeTarget(null);\n htmlTextArea.style.height = (0.8 * document.documentElement.clientHeight) + 'px';\n htmlTextArea.value = canvas.innerHTML;\n dom.show(htmlTextArea);\n dom.hide(canvas);\n sourceOpen = true;\n plugins('onSourceOpen', htmlTextArea);\n }\n\n /**\n * The textarea's html back into the canvas. innerHTML, so a <script>\n * typed into the source is markup like any other and does not run in\n * the editor; the page it is published on runs it.\n */\n function closeSource() {\n plugins('onSourceClose', htmlTextArea);\n sourceOpen = false;\n dom.setHtml(canvas, htmlTextArea.value);\n dom.show(canvas);\n init();\n dom.hide(htmlTextArea);\n }\n\n /**\n * What can be the active target: a column, or a plugin's region - a\n * section. Not the canvas, which is where the toolbar adds without one.\n */\n function targetSelector() {\n return ['.column'].concat(pluginHooks('regions')).join(', ');\n }\n\n function isTarget(node) {\n return !!node && node !== canvas && canvas.contains(node) && dom.is(node, targetSelector());\n }\n\n /** The one way the active target changes, told only when it does. */\n function changeTarget(node) {\n if (node === activeTarget) { return; }\n\n var from = activeTarget;\n if (from) { dom.removeClass(from, 'ge-active-target'); }\n activeTarget = node;\n if (node && dom.hasClass(canvas, 'ge-editing')) { dom.addClass(node, 'ge-active-target'); }\n\n emit('target-change', { canvas: canvas, target: node, from: from });\n }\n\n /**\n * A toolbar button's click with an active target: what it makes goes\n * where a drop at the target's end would put it.\n */\n function addToTarget(button, source) {\n var made = insertFromToolbar(button, { region: activeTarget, before: null }, source);\n if (made && made.scrollIntoView) { made.scrollIntoView({ behavior: 'smooth' }); }\n }\n\n function init() {\n // The node whose settings were open is gone - deleted, say - and\n // its panel with it\n if (openSettingsState && !dom.attached(openSettingsState.node)) {\n closeSettings();\n }\n // And a dialog showing part of a panel that is gone\n if (dialogState && dialogState.home && !dom.attached(dialogState.home)) {\n closeDialog();\n }\n\n runFilter(true);\n dom.addClass(canvas, 'ge-editing');\n dom.toggleClass(canvas, 'ge-drag-drawer', settings.drag_handle === 'drawer');\n addAllColClasses();\n var cutter = textCutter();\n splitTexts(cutter);\n wrapContent(cutter);\n wrapTexts();\n createRowControls();\n createColControls();\n markContainers();\n plugins('onInit');\n makeSortable();\n makeResizable();\n switchLayout(curView);\n refreshPreviews(canvas);\n\n // Deleted, or taken out some other way, it is a target no more\n if (activeTarget && !canvas.contains(activeTarget)) {\n changeTarget(null);\n } else if (activeTarget) {\n dom.addClass(activeTarget, 'ge-active-target');\n }\n }\n\n function deinit() {\n // Its panel goes home to its drawer first, and both go together\n closeSettings();\n dom.removeClass(canvas, 'ge-editing ge-drag-drawer ge-dropping');\n // The mark goes, the target stays: getHtml comes straight back\n if (activeTarget) { dom.removeClass(activeTarget, 'ge-active-target'); }\n // Before the drawers and the text blocks come off: an editor\n // plugin closes its editors here, and finds them where it left them\n plugins('onBeforeDeinit');\n closeSizePicker();\n hideDropMarker();\n // In case a dialog was opened with no settings panel open\n closeDialog();\n removeDrawers(canvas);\n pluginFields.clear();\n unwrapTexts(canvas);\n plugins('onDeinit');\n // After the rich text editors have let go of their content areas:\n // one that rebuilt its area's DOM brought the preview styles back\n // with it, and the attribute recording them came back too\n clearPreviews(canvas);\n clearRowCols(canvas);\n unmarkContainers();\n removeSortable();\n removeResizable();\n runFilter(false, canvas);\n }\n\n function removeDrawers(root) {\n dom.all(root, '.ge-tools-drawer').forEach(function(drawer) { drawer.remove(); });\n }\n\n function clearRowCols(root) {\n dom.all(root, '[data-ge-row-cols]').forEach(function(row) { row.removeAttribute('data-ge-row-cols'); });\n }\n\n /**\n * The plugins that cannot be read without the canvas leaving editing:\n * the ones that put something on the canvas - an unmark, an onDeinit\n * or an onBeforeDeinit takes it off - and say nothing of how to take\n * it off a copy.\n */\n function pluginsWithoutCleanMarkup() {\n var names = [];\n\n [CONTAINERS, FEATURES, UTILITIES].forEach(function(registry) {\n Object.keys(registry).forEach(function(name) {\n var plugin = registry[name];\n var marks = plugin.unmark || plugin.onDeinit || plugin.onBeforeDeinit;\n if (marks && !plugin.cleanMarkup) { names.push(name); }\n });\n });\n\n return names;\n }\n\n /**\n * A copy of the canvas, and the way from each of its elements back to\n * the one it was copied from. The two trees are walked side by side,\n * which works because a deep clone has the same shape.\n */\n function copyCanvas() {\n var copy = canvas.cloneNode(true);\n var toLive = new Map();\n var toCopy = new Map();\n var live = document.createTreeWalker(canvas, NodeFilter.SHOW_ELEMENT);\n var copied = document.createTreeWalker(copy, NodeFilter.SHOW_ELEMENT);\n var a = live.currentNode;\n var b = copied.currentNode;\n\n while (a && b) {\n toLive.set(b, a);\n toCopy.set(a, b);\n a = live.nextNode();\n b = copied.nextNode();\n }\n\n return {\n root: copy,\n liveOf: function(node) { return toLive.get(node) || null; },\n copyOf: function(node) { return toCopy.get(node) || null; },\n };\n }\n\n /**\n * getHtml without the canvas leaving editing: what deinit takes off,\n * taken off a copy, so the text being typed into, the settings panel\n * and the focus are where they were. The same markup getHtml gives,\n * or getHtml itself - with a word, once - when a plugin can only take\n * its marking off the canvas, or will not this time.\n */\n function snapshotHtml() {\n // Nothing is being edited to keep: the canvas is out of editing\n if (sourceOpen) { return getHtml(); }\n\n var missing = pluginsWithoutCleanMarkup();\n if (missing.length) {\n missing.forEach(function(name) {\n warnOnceHere('snapshot:' + name, 'the \"' + name + '\" plugin has no cleanMarkup, so the canvas ' +\n 'leaves editing to be read: open texts and settings panels close');\n });\n return getHtml();\n }\n\n var copy = copyCanvas();\n var root = copy.root;\n\n [root].concat(dom.all(root, '.ge-active-target, .ge-settings-target')).forEach(function(node) {\n dom.removeClass(node, 'ge-active-target ge-settings-target');\n dom.dropEmptyClass(node);\n });\n dom.all(root, '.ge-drop-marker').forEach(function(marker) { marker.remove(); });\n removeDrawers(root);\n unwrapTexts(root);\n\n var refused = null;\n [CONTAINERS, FEATURES, UTILITIES].forEach(function(registry) {\n Object.keys(registry).forEach(function(name) {\n var plugin = registry[name];\n if (refused || !plugin.cleanMarkup) { return; }\n if (plugin.cleanMarkup(root, copy.liveOf) === false) { refused = name; }\n });\n });\n\n if (refused) {\n warnOnceHere('snapshot-refused:' + refused, 'the \"' + refused + '\" plugin cannot take its marking off ' +\n 'a copy right now, so the canvas leaves editing to be read');\n return getHtml();\n }\n\n clearPreviews(root);\n clearRowCols(root);\n dom.all(root, '[data-ge-container]').forEach(unmarkContainerClasses);\n sortables.forEach(function(sortableInstance) {\n var list = copy.copyOf(sortableInstance.el);\n if (list) { dom.all(list, '[draggable]').forEach(function(node) { node.removeAttribute('draggable'); }); }\n });\n removeResizeFurniture(root);\n runFilter(false, root);\n stripPixelWidths(root);\n\n return root.innerHTML;\n }\n\n /**\n * The markup as a host would save it: no drawers, no editor, no\n * sortables. The canvas goes back to editing afterwards.\n */\n function getHtml(options) {\n if (options && options.keepEditing) { return snapshotHtml(); }\n\n deinit();\n stripPixelWidths(canvas);\n var html = canvas.innerHTML;\n init();\n return html;\n }\n\n /**\n * One node's markup, as getHtml would give it: the canvas goes out of\n * editing to read it and comes back, as it does for getHtml.\n */\n function nodeHtml(node) {\n deinit();\n stripPixelWidths(node);\n var html = node.outerHTML;\n init();\n return html;\n }\n\n /** getHtml with grid-editor's own classes and attributes taken off. */\n function getPlainHtml(options) {\n return plainHtml(getHtml(options));\n }\n\n /**\n * ge.setHtml(): the canvas made of other markup, and edited again. Not\n * an add or a delete of anything, so no events: what was there is\n * replaced as a whole. innerHTML, as the source view does, so a\n * <script> in it is markup and does not run in the editor.\n */\n function setHtml(html) {\n // What is in the textarea is not wanted - html replaces it - but\n // the source view closes the one way it always does\n if (sourceOpen) {\n closeSource();\n if (mainControls) {\n dom.all(mainControls, '.gm-edit-mode').forEach(function(button) {\n dom.removeClass(button, 'active btn-danger');\n });\n }\n }\n\n deinit();\n dom.setHtml(canvas, html);\n init();\n }\n\n /**\n * Take the editor off the canvas: the markup stays, as getHtml would\n * give it, and everything the editor added - controls, panels,\n * listeners - goes. Safe on a canvas already taken out of the page,\n * as a framework tearing a component down does.\n */\n function destroy() {\n // First, while the editor is whole: a plugin may still read it\n plugins('onDestroy');\n // The html being edited is what the canvas is left with\n if (sourceOpen) { closeSource(); }\n deinit();\n activeTarget = null;\n removeConfirmModal();\n removeSettingsPanels();\n removeDialog();\n removeMainControls();\n htmlTextArea.remove();\n lifetime.abort();\n instances.delete(canvas);\n destroyed = true;\n }\n\n /**\n * The plugins this editor is using: the ones registered by the files\n * the page loaded, narrowed by the plugins setting.\n *\n * Each is a factory, called once here with the handle it works\n * through. Everything a plugin needs from the editor goes through\n * that handle, because the closure it runs outside of is not\n * something it can see.\n */\n function loadPlugins() {\n var api = pluginApi();\n\n registerFamily('grid', {}, widthFamily());\n if (settings.row_cols !== false) { registerFamily('grid', {}, rowColsFamily()); }\n var wanted = function(name) {\n return !settings.plugins || settings.plugins.indexOf(name) !== -1;\n };\n\n // What the plugins setting does not choose: the text editors,\n // which content_types chooses. A page that names its containers\n // there has named no editor, and still wants the one it uses.\n var featureWanted = function(name, factory) {\n return factory.always === true || wanted(name);\n };\n\n Object.keys(GridEditor.containers).forEach(function(type) {\n if (wanted(type)) { CONTAINERS[type] = GridEditor.containers[type](api); }\n });\n\n Object.keys(GridEditor.features).forEach(function(name) {\n var factory = GridEditor.features[name];\n if (featureWanted(name, factory)) { FEATURES[name] = factory(api); }\n });\n\n Object.keys(GridEditor.utilities).forEach(function(name) {\n if (!wanted(name)) { return; }\n\n UTILITIES[name] = GridEditor.utilities[name](api);\n (UTILITIES[name].families || []).forEach(function(family) {\n registerFamily(name, UTILITIES[name], family);\n });\n });\n\n Object.keys(FEATURES).forEach(function(name) {\n var methods = FEATURES[name].methods || {};\n Object.keys(methods).forEach(function(method) {\n featureMethods[method] = methods[method];\n });\n });\n\n (settings.plugins || []).forEach(function(name) {\n if (CONTAINERS[name] || FEATURES[name] || UTILITIES[name]) { return; }\n\n warnOnceHere('plugin:' + name, 'the \"' + name + '\" plugin is not loaded: ' +\n 'include dist/plugins/grideditor.' + name + '.js after the editor');\n });\n }\n\n /**\n * A hook every loaded plugin may have. Containers first, since a\n * feature that looks at the canvas - elements, say - wants the\n * containers already marked, and utilities last, since they decorate\n * nodes the other two may have just made.\n */\n function plugins(hook, argument) {\n [CONTAINERS, FEATURES, UTILITIES].forEach(function(registry) {\n Object.keys(registry).forEach(function(name) {\n if (registry[name][hook]) { registry[name][hook](argument); }\n });\n });\n }\n\n /** What a plugin is handed. See docs/plugins.md. */\n function pluginApi() {\n return {\n canvas: canvas,\n settings: settings,\n t: t,\n warn: warn,\n containerId: containerId,\n defaultRegion: defaultRegion,\n createTool: createTool,\n createMoveTool: createMoveTool,\n addSettingsTool: addSettingsTool,\n deleteNode: deleteNode,\n place: place,\n createPaneControls: createPaneControls,\n makeLabelEditable: makeLabelEditable,\n labelIn: labelIn,\n unwrapLabels: unwrapLabels,\n suspendToggles: suspendToggles,\n resumeToggles: resumeToggles,\n emit: emit,\n payloadFor: payloadFor,\n operate: operate,\n kindOf: kindOf,\n view: getView,\n viewTiers: function() {\n return tiersFor(curView).map(function(tier) { return tier.key; });\n },\n breakpoints: BREAKPOINTS.map(function(tier) { return tier.key; }),\n getUtility: getUtility,\n setUtility: setUtility,\n utilityField: utilityField,\n bareStyle: bareStyle,\n // The host's own style, under the preview\n hostStyle: hostStyle,\n setHostStyle: setHostStyle,\n // A modal of the editor's own, over the settings\n openDialog: openDialog,\n closeDialog: closeDialog,\n rowFromLayout: rowFromLayoutValue,\n nodeHtml: nodeHtml,\n // The markup as getHtml gives it, with the canvas left editing\n snapshotHtml: snapshotHtml,\n setHtml: setHtml,\n // A question in the editor's confirm modal\n confirm: confirmWith,\n // A text editor has rewritten a content area, so whatever the\n // editor and its plugins had put in there goes back in\n textReady: textReady,\n // A choice under a tool, offered by holding it\n attachPicker: attachPicker,\n openPicker: openPicker,\n closePicker: closeSizePicker,\n // A node's settings panel, in its drawer or open outside it\n detailsOf: detailsOf,\n // A node's drawer: its first child, or for a content area the\n // one beside it in its text block\n drawerOf: drawerOf,\n // The toolbar built again, from the plugins' toolbars as they are now\n refreshToolbar: refreshToolbar,\n toolbarItems: function(name) {\n return mainControls\n ? dom.all(mainControls, '[data-ge-toolbar=\"feature\"][data-ge-feature=\"' + name + '\"]')\n : [];\n },\n };\n }\n\n function drawerOf(node) {\n if (dom.hasClass(node, 'ge-content')) {\n var textBlock = node.parentElement;\n return dom.hasClass(textBlock, 'ge-text-block') ? dom.child(textBlock, '.ge-tools-drawer') : null;\n }\n\n return dom.child(node, '.ge-tools-drawer');\n }\n\n /* --------------------------------------------------------------\n * Utilities: Bootstrap's responsive utility classes.\n *\n * A utility plugin declares families - order, d, justify-content -\n * and this is everything that reads or writes one. Every family is\n * spelled the way Bootstrap spells them all, {prefix}-{infix}-{value}\n * with no infix at the smallest tier, and cascades the way the size\n * classes do: a tier that says nothing takes the nearest smaller one.\n *\n * The canvas cannot show a breakpoint's utilities by itself. A\n * per-breakpoint view narrows the canvas, not the viewport, and\n * Bootstrap's utilities answer to the viewport with !important. So\n * each node gets what its classes mean at the view being edited,\n * as inline !important styles, recorded in an attribute so they come\n * off again - exactly those, leaving the host's own style alone.\n * -------------------------------------------------------------- */\n\n var FAMILIES = {}; // Every family the utility plugins declare, by name\n var UTILITY_NODES = '.row, .column, .ge-content, .ge-element, [data-ge-container]';\n var PREVIEW_ATTR = 'data-ge-preview';\n var utilitiesOpen = false; // Whether the panels show their Responsive section unfolded\n\n function registerFamily(pluginName, utility, family) {\n var name = family.name || family.prefix;\n\n if (FAMILIES[name]) {\n warn('the \"' + pluginName + '\" plugin declares the utility \"' + name +\n '\", which the \"' + FAMILIES[name].plugin + '\" plugin already declared: ignored');\n return;\n }\n\n FAMILIES[name] = {\n plugin: pluginName,\n family: Object.assign({}, family, {\n name: name,\n values: family.values.map(String),\n appliesTo: family.appliesTo || utility.appliesTo || ['row', 'column'],\n }),\n };\n }\n\n /** The family a caller named, or null and a warning when no plugin declares it. */\n function familyNamed(name, method) {\n if (FAMILIES[name]) { return FAMILIES[name].family; }\n\n warnOnceHere('utility:' + name, method + '(' + JSON.stringify(name) + '): no loaded ' +\n 'plugin declares that utility');\n return null;\n }\n\n /**\n * Whether a family applies to a kind of node. A container answers to\n * `container` and to its own type, so a plugin can take them all or\n * name the ones it means.\n */\n function appliesTo(family, kind) {\n // The host's plain content reads and previews its utilities as a\n // text does; with no gear, nothing in its drawer writes them\n if (kind === 'plain') { kind = 'text'; }\n if (family.appliesTo.indexOf(kind) !== -1) { return true; }\n\n return !!CONTAINERS[kind] && family.appliesTo.indexOf('container') !== -1;\n }\n\n function familiesFor(kind) {\n return Object.keys(FAMILIES).map(function(name) {\n return FAMILIES[name].family;\n }).filter(function(family) {\n return appliesTo(family, kind);\n });\n }\n\n function utilityClass(family, tier, value) {\n if (family.className) { return family.className(tier.key, value); }\n\n return family.prefix + (tier.infix ? '-' + tier.infix : '') + '-' + value;\n }\n\n /** The value a node carries a class for at exactly this tier, or null. */\n function ownUtility(node, family, tier) {\n var classes = (node.getAttribute('class') || '').split(/\\s+/);\n\n for (var i = 0; i < family.values.length; i++) {\n if (classes.indexOf(utilityClass(family, tier, family.values[i])) !== -1) {\n return family.values[i];\n }\n }\n\n return null;\n }\n\n /**\n * The tier below this one that decides the value here, and what it\n * says, when this tier says nothing itself. Null when nothing below\n * says anything either.\n */\n function inheritedUtility(node, family, tier) {\n for (var i = BREAKPOINTS.indexOf(tier) - 1; i >= 0; i--) {\n var value = ownUtility(node, family, BREAKPOINTS[i]);\n if (value !== null) { return { tier: BREAKPOINTS[i], value: value }; }\n }\n\n return null;\n }\n\n /** What applies at a tier: its own class, or what it inherits. */\n function effectiveUtility(node, family, tier) {\n var own = ownUtility(node, family, tier);\n if (own !== null) { return own; }\n\n var inherited = inheritedUtility(node, family, tier);\n return inherited ? inherited.value : null;\n }\n\n /** Every tier the node carries a class of this family for. */\n function utilityTiers(node, family) {\n return BREAKPOINTS.map(function(tier) {\n return { tier: tier, value: ownUtility(node, family, tier) };\n }).filter(function(entry) { return entry.value !== null; });\n }\n\n function writeUtility(node, family, tier, value) {\n family.values.forEach(function(candidate) {\n dom.removeClass(node, utilityClass(family, tier, candidate));\n });\n\n if (value !== null) { dom.addClass(node, utilityClass(family, tier, value)); }\n dom.dropEmptyClass(node);\n }\n\n /**\n * What a view reads. A breakpoint reads what applies there. The all\n * view reads the class with no infix, since that is what it writes:\n * the one class that means \"the same at every size\".\n */\n function readUtility(node, family, view) {\n return view === ALL_VIEW\n ? ownUtility(node, family, BREAKPOINTS[0])\n : effectiveUtility(node, family, breakpoint(view));\n }\n\n /**\n * What writing `value` in a view comes to, or null when it changes\n * nothing. A breakpoint writes its own tier and nothing else. The all\n * view writes the class with no infix and clears the family from\n * every other tier, and says what it cleared: choosing one value for\n * every size is choosing it over what the sizes said.\n */\n function planUtility(node, family, view, value) {\n if (view !== ALL_VIEW) {\n var tier = breakpoint(view);\n if (ownUtility(node, family, tier) === value) { return null; }\n\n return { writes: [{ tier: tier, value: value }], cleared: [] };\n }\n\n var writes = [];\n var cleared = [];\n\n utilityTiers(node, family).forEach(function(entry) {\n if (entry.tier === BREAKPOINTS[0]) { return; }\n\n writes.push({ tier: entry.tier, value: null });\n cleared.push({ breakpoint: entry.tier.key, value: entry.value });\n });\n\n if (ownUtility(node, family, BREAKPOINTS[0]) !== value) {\n writes.unshift({ tier: BREAKPOINTS[0], value: value });\n }\n\n return writes.length ? { writes: writes, cleared: cleared } : null;\n }\n\n /** getUtility(node, family, view?): the value that applies, or null. */\n function getUtility(node, name, view) {\n node = nodeFrom(node);\n\n var family = familyNamed(name, 'getUtility');\n if (!family || !node) { return null; }\n\n var key = view === undefined ? curView : viewKey(view);\n if (key === null) {\n warn('getUtility(' + JSON.stringify(view) + '): no such layout mode');\n return null;\n }\n\n return readUtility(node, family, key);\n }\n\n /**\n * setUtility(node, family, value, view?): write a value through the\n * events. Null is \"inherit\". The last argument is a view key, or\n * { view, source } from a plugin that wants its tool named in the\n * payload. False when a handler canceled or nothing changed.\n */\n function setUtility(node, name, value, options) {\n options = typeof options == 'string' ? { view: options } : (options || {});\n node = nodeFrom(node);\n\n var family = familyNamed(name, 'setUtility');\n if (!family || !node) { return false; }\n\n var view = options.view === undefined ? curView : viewKey(options.view);\n if (view === null) {\n warn('setUtility(' + JSON.stringify(options.view) + '): no such layout mode');\n return false;\n }\n\n value = value === null || value === undefined || value === '' ? null : String(value);\n if (value !== null && family.values.indexOf(value) === -1) {\n warn('setUtility: ' + JSON.stringify(value) + ' is not a value of \"' + name +\n '\", which takes ' + JSON.stringify(family.values));\n return false;\n }\n\n var kind = kindOf(node);\n if (!appliesTo(family, kind)) {\n warn('setUtility: \"' + name + '\" does not apply to a ' + kind);\n return false;\n }\n\n // A family whose writes are some other operation - the column\n // width, which is a resize - does them its own way\n if (family.write) { return family.write(node, value, view, options.source || 'api'); }\n\n var plan = planUtility(node, family, view, value);\n if (!plan) { return false; }\n\n return operate(function() {\n var payload = payloadFor(kind, node, {\n family: name,\n breakpoint: view,\n tiers: plan.writes.map(function(write) { return write.tier.key; }),\n from: readUtility(node, family, view),\n to: value,\n cleared: plan.cleared,\n source: options.source || 'api',\n });\n\n if (!emit('before-utility', payload)) {\n // The panel already shows the value that was refused\n refreshUtilities(node);\n return false;\n }\n\n plan.writes.forEach(function(write) {\n writeUtility(node, family, write.tier, write.value);\n });\n refreshUtilities(node);\n emit('after-utility', payload);\n\n return true;\n });\n }\n\n /**\n * ge.bareStyle(node, family, property): what a css property comes to\n * on a node with none of the family's classes, at any breakpoint. The\n * answer a preview needs for \"no class applies here\" when that is not\n * a constant: text-align inherits from the parent, and the host's own\n * css may float an element. The browser is the only one who knows, so\n * the classes come off for the moment it takes to ask.\n */\n function bareStyle(node, name, property) {\n var family = familyNamed(name, 'bareStyle');\n node = nodeFrom(node);\n if (!family || !node) { return null; }\n\n var original = node.getAttribute('class');\n BREAKPOINTS.forEach(function(tier) { writeUtility(node, family, tier, null); });\n\n var value = getComputedStyle(node).getPropertyValue(property);\n\n if (original === null) { node.removeAttribute('class'); } else { node.setAttribute('class', original); }\n\n return value;\n }\n\n /** Bring a node's panel and preview up to date with its classes. */\n function refreshUtilities(node) {\n var details = detailsOf(node);\n\n if (details) {\n var classes = dom.one(details, '.ge-classes');\n if (classes) { classes.value = hostClasses(node).join(' '); }\n dom.children(details, '.ge-utilities').forEach(function(section) { renderUtilities(section); });\n }\n renderPluginFields(node);\n refreshPreviews(node);\n }\n\n /* Preview */\n\n function utilityNodes(scope) {\n return dom.selfAndAll(scope, UTILITY_NODES);\n }\n\n /**\n * Put what each node's utilities mean at the view being edited on the\n * node itself. Only nodes that carry a class of a family get anything,\n * and they get the family's answer for the view even when that is\n * \"nothing\": a wider tier's class is still live in a wide window, and\n * has to be overruled.\n *\n * The all view gets nothing. Its canvas is not narrowed, every tier is\n * live, and what Bootstrap shows is the truth.\n */\n function refreshPreviews(scope) {\n clearPreviews(scope);\n\n if (curView !== ALL_VIEW) { previewTier(scope, breakpoint(curView)); }\n\n markRowCols(scope);\n\n // Whatever a plugin marks the canvas with to show its utilities\n // goes stale at the same moments the preview does\n plugins('onRefresh', scope);\n }\n\n function previewTier(scope, tier) {\n utilityNodes(scope).forEach(function(node) {\n var kind = kindOf(node);\n var styles = {};\n\n familiesFor(kind).forEach(function(family) {\n if (!family.preview || !utilityTiers(node, family).length) { return; }\n\n Object.assign(styles, family.preview(effectiveUtility(node, family, tier), node, kind));\n });\n\n if (kind === 'column') { Object.assign(styles, rowColsPreview(node, tier)); }\n\n // A plugin whose families settle one property between them\n // previews the node as a whole\n Object.keys(UTILITIES).forEach(function(name) {\n var utility = UTILITIES[name];\n if (utility.preview) { Object.assign(styles, utility.preview(node, kind, tier.key)); }\n });\n\n if (Object.keys(styles).length) { applyPreview(node, styles); }\n });\n }\n\n /**\n * Set inline !important styles, which is the one thing that beats\n * Bootstrap's own !important, and remember what each property was so\n * it can be put back. The record is an attribute because a rich text\n * editor rebuilds the DOM of the area it edits, and the record has to\n * come back with the node.\n */\n function applyPreview(node, styles) {\n var style = node.style;\n var was = {};\n\n Object.keys(styles).forEach(function(property) {\n was[property] = [style.getPropertyValue(property), style.getPropertyPriority(property)];\n style.setProperty(property, String(styles[property]), 'important');\n });\n\n node.setAttribute(PREVIEW_ATTR, JSON.stringify(was));\n }\n\n function clearPreviews(scope) {\n dom.selfAndAll(scope, '[' + PREVIEW_ATTR + ']').forEach(function(node) {\n var style = node.style;\n var was = {};\n\n try { was = JSON.parse(node.getAttribute(PREVIEW_ATTR)) || {}; } catch (error) { /* a mangled record: drop it */ }\n\n Object.keys(was).forEach(function(property) {\n var before = was[property];\n\n if (before && before[0]) {\n style.setProperty(property, before[0], before[1]);\n } else {\n style.removeProperty(property);\n }\n });\n\n node.removeAttribute(PREVIEW_ATTR);\n dom.dropEmptyStyle(node);\n });\n }\n\n /* The host's own style, under the preview */\n\n /**\n * The node's style as the host wrote it: its declarations with every\n * property the preview set put back to what the preview recorded.\n * Held in a detached element's style, which parses and serializes it\n * the way the node's own would.\n */\n function hostDeclaration(node) {\n var scratch = document.createElement('div');\n var was = {};\n\n scratch.style.cssText = node.style.cssText;\n try { was = JSON.parse(node.getAttribute(PREVIEW_ATTR)) || {}; } catch (error) { /* no record */ }\n\n Object.keys(was).forEach(function(property) {\n var before = was[property];\n\n if (before && before[0]) {\n scratch.style.setProperty(property, before[0], before[1]);\n } else {\n scratch.style.removeProperty(property);\n }\n });\n\n return scratch.style;\n }\n\n /**\n * ge.hostStyle(node, property): { value, priority } of one property\n * of the host's style, never the preview's. With no property, the\n * host's whole style as css text.\n */\n function hostStyle(node, property) {\n var declaration = hostDeclaration(node);\n\n if (property === undefined) { return declaration.cssText; }\n\n return {\n value: declaration.getPropertyValue(property),\n priority: declaration.getPropertyPriority(property),\n };\n }\n\n /**\n * ge.setHostStyle(node, property, value, priority): write one property\n * of the host's style, or take it off with an empty value. The\n * preview comes off the node while it is written and goes back on\n * after, so what the preview put back on deinit is the host's new\n * value. False, and nothing written, when the browser refuses the\n * value. `priority` left out keeps the one the property had.\n */\n function setHostStyle(node, property, value, priority) {\n value = value === null || value === undefined ? '' : String(value).trim();\n\n if (priority === undefined) { priority = hostStyle(node, property).priority; }\n\n if (value !== '') {\n var check = document.createElement('div').style;\n check.setProperty(property, value, priority || '');\n if (check.getPropertyValue(property) === '') { return false; }\n }\n\n var previewed = node.hasAttribute(PREVIEW_ATTR);\n if (previewed) { clearPreviews(node); }\n\n if (value === '') {\n node.style.removeProperty(property);\n } else {\n node.style.setProperty(property, value, priority || '');\n }\n dom.dropEmptyStyle(node);\n\n if (previewed) { refreshPreviews(node); }\n\n return true;\n }\n\n /* The panel */\n\n /**\n * The Responsive section of a node's settings panel: one field per\n * family that applies to the node, reading and writing the view being\n * edited, and whatever fields a plugin builds itself. Folded until the\n * user unfolds one, and then unfolded on every node, since whoever\n * wanted it on one wants it on the next.\n */\n function createUtilitiesSection(node) {\n var kind = kindOf(node);\n var fields = familiesFor(kind)\n .filter(function(family) { return family.panel !== false; })\n .map(function(family) { return createField(node, family); });\n\n Object.keys(UTILITIES).forEach(function(name) {\n var utility = UTILITIES[name];\n var own = utility.panel ? utility.panel(node, kind) : null;\n if (own) { fields.push(own); }\n });\n\n if (!fields.length) { return null; }\n\n var section = dom.toggleClass(dom.element('div', { 'class': 'ge-utilities' }), 'ge-open', utilitiesOpen);\n sectionNodes.set(section, node);\n\n var toggle = section.appendChild(dom.element('a', { 'class': 'ge-utilities-toggle' }));\n toggle.addEventListener('click', function() {\n utilitiesOpen = !dom.hasClass(section, 'ge-open');\n settingsScope().forEach(function(scope) {\n dom.all(scope, '.ge-utilities').forEach(function(each) {\n dom.toggleClass(each, 'ge-open', utilitiesOpen);\n });\n });\n });\n\n var body = section.appendChild(dom.element('div', { 'class': 'ge-utilities-body' }));\n fields.forEach(function(field) { body.appendChild(field); });\n\n renderUtilities(section);\n\n return section;\n }\n\n /**\n * One family's field: its label, a select that writes through\n * setUtility, and a note. Filled by renderField, again whenever the\n * view or the node's classes change.\n */\n function createField(node, family) {\n var field = dom.element('label', { 'class': 'ge-utility', 'data-ge-family': family.name });\n\n field.appendChild(dom.element('span', { 'class': 'ge-utility-label' },\n family.labelKey ? t(family.labelKey) : family.name));\n\n var select = field.appendChild(dom.element('select', { 'class': 'form-select form-select-sm' }));\n select.addEventListener('change', function() {\n setUtility(node, family.name, this.value, { source: 'panel' });\n });\n\n field.appendChild(dom.element('small', { 'class': 'ge-utility-note' }));\n\n return field;\n }\n\n /** ge.utilityField(node, family): a field a plugin places in a panel of its own. */\n function utilityField(node, name) {\n var family = familyNamed(name, 'utilityField');\n if (!family) { return null; }\n\n var field = createField(node, family);\n renderField(field, node);\n pluginFields.set(field, node);\n\n return field;\n }\n\n /**\n * The fields a plugin made, wherever it put them: a Responsive\n * section renders its own, and these are the rest - in a plugin's\n * section of the panel, or in the dialog. Each one's node's, or\n * every node's; a field no longer on the page is forgotten.\n */\n var pluginFields = new Map(); // field -> the node it edits\n\n function renderPluginFields(node) {\n pluginFields.forEach(function(fieldNode, field) {\n if (!field.isConnected) {\n pluginFields.delete(field);\n return;\n }\n if (node && fieldNode !== node) { return; }\n if (dom.closest(field, '.ge-utilities')) { return; }\n\n renderField(field, fieldNode);\n });\n }\n\n /** Fill a section's fields, the families' and the plugins' own, for the view being edited. */\n function renderUtilities(section) {\n var node = sectionNodes.get(section);\n\n dom.children(section, '.ge-utilities-toggle').forEach(function(toggle) {\n toggle.textContent = t('utility.section', { view: t(labelKeyFor(curView)) });\n });\n\n dom.all(section, '.ge-utility').forEach(function(field) { renderField(field, node); });\n }\n\n function renderField(field, node) {\n var family = FAMILIES[field.getAttribute('data-ge-family')].family;\n var select = dom.child(field, 'select');\n var choices = family.choices ? family.choices(node, kindOf(node)) : family.values;\n var own, blank, note = '';\n\n select.innerHTML = '';\n\n if (curView === ALL_VIEW) {\n own = ownUtility(node, family, BREAKPOINTS[0]);\n blank = t('utility.default');\n\n var varies = utilityTiers(node, family).filter(function(entry) {\n return entry.tier !== BREAKPOINTS[0];\n });\n if (varies.length) {\n note = t('utility.varies', {\n breakpoints: varies.map(function(entry) { return entry.tier.key; }).join(', '),\n });\n }\n } else {\n var tier = breakpoint(curView);\n var inherited = inheritedUtility(node, family, tier);\n\n own = ownUtility(node, family, tier);\n blank = inherited\n ? t('utility.inherit', { value: labelOf(family, inherited.value), breakpoint: inherited.tier.key })\n : t('utility.default');\n\n // What the empty choice means is sometimes not the family's\n // own business: a column's width can come from its row\n var custom = family.blank ? family.blank(node, curView) : null;\n if (custom && own === null) { blank = custom; }\n }\n\n // A value the markup carries is shown even when the family\n // would not offer it here, rather than shown as something else\n if (own !== null && choices.indexOf(own) === -1) { choices = choices.concat([own]); }\n\n select.appendChild(dom.element('option', { value: '' }, blank));\n choices.forEach(function(value) {\n select.appendChild(dom.element('option', { value: value }, labelOf(family, value)));\n });\n\n select.value = own === null ? '' : own;\n\n var noteNode = dom.child(field, '.ge-utility-note');\n noteNode.textContent = note;\n dom.toggle(noteNode, note !== '');\n }\n\n function labelOf(family, value) {\n return family.label ? family.label(value) : value;\n }\n\n /* --------------------------------------------------------------\n * Containers: tabs, accordions, popups, carousels and cards.\n *\n * A container holds panes, and a pane is an ordinary canvas region -\n * rows, columns, content areas and elements nest inside one exactly\n * as they do at the top level, because init() walks the whole canvas\n * and does not care how deep it is.\n *\n * What a container is, is said by data-ge-container. The ge-* classes\n * are editing furniture and come off with everything else, so a host\n * restyling the markup cannot break detection and getHtml stays clean.\n * -------------------------------------------------------------- */\n\n var CONTAINERS = {}; // The container plugins in use, by the type each builds\n var FEATURES = {}; // The feature plugins in use, by name\n var UTILITIES = {}; // The utility plugins in use, by name\n var featureMethods = {}; // The methods those features contribute\n var containerCounter = 0;\n\n /**\n * Ids go into the markup rather than into memory: Bootstrap's toggles\n * are written in terms of them, and the markup has to survive getHtml\n * with those toggles still pointing at the right panes.\n */\n function containerId(type) {\n containerCounter++;\n\n return 'ge-' + type + '-' + containerCounter + '-' +\n Math.random().toString(36).slice(2, 6);\n }\n\n /** A pane's starting content: one full width column, ready to edit. */\n function defaultRegion() {\n var row = createRow();\n row.appendChild(createColumn(MAX_COL_SIZE));\n return row;\n }\n\n function containerTypeOf(container) {\n return container ? container.getAttribute('data-ge-container') : null;\n }\n\n function markContainers() {\n dom.all(canvas, '[data-ge-container]').forEach(function(container) {\n var type = containerTypeOf(container);\n var definition = CONTAINERS[type];\n\n if (!definition) {\n warnOnceHere('container:' + type, 'unknown container type \"' + type + '\"');\n return;\n }\n\n dom.addClass(container, 'ge-container ge-container-' + type);\n definition.mark(container);\n\n if (!dom.child(container, '.ge-tools-drawer')) {\n createContainerControls(container, type, definition);\n }\n });\n }\n\n function unmarkContainers() {\n dom.all(canvas, '[data-ge-container]').forEach(function(container) {\n var definition = CONTAINERS[containerTypeOf(container)];\n\n if (definition) { definition.unmark(container); }\n\n unmarkContainerClasses(container);\n });\n }\n\n function unmarkContainerClasses(container) {\n dom.removeClass(container, 'ge-container ge-container-' + containerTypeOf(container));\n dom.dropEmptyClass(container);\n }\n\n /** A new drawer as the first child of `node`. */\n function prependDrawer(node, className) {\n var drawer = dom.element('div', { 'class': className });\n node.insertBefore(drawer, node.firstChild);\n return drawer;\n }\n\n /** The host's own tools, from a *_tools setting, in a drawer. */\n function hostTools(drawer, tools) {\n (tools || []).forEach(function(hostTool) {\n createTool(drawer, hostTool.title || '', hostTool.className || '',\n hostTool.iconClass || 'bi bi-wrench', hostTool.on);\n });\n }\n\n function createContainerControls(container, type, definition) {\n var drawer = prependDrawer(container, 'ge-tools-drawer ge-container-drawer');\n\n createMoveTool(drawer);\n addSettingsTool(drawer, container, settings.container_classes);\n\n hostTools(drawer, settings.container_tools);\n\n if (definition.tools) { definition.tools(drawer, container); }\n\n createTool(drawer, t('tool.delete_container'), 'ge-delete-container', 'bi bi-trash', function() {\n deleteNode(type, container, t('confirm.delete_container'), function(removed) {\n dom.slideUp(container, removed);\n });\n });\n\n // Delete then add, the order rows and columns have\n if (definition.addPane) {\n createTool(drawer, t(definition.addPaneKey), 'ge-add-pane', 'bi bi-plus-circle', function() {\n var pane = definition.addPane(container, {});\n if (!pane) { return; }\n\n addNode(definition.paneKind, pane, function() {}, {\n parent: container,\n source: 'tool',\n container: container,\n });\n });\n }\n }\n\n /**\n * A pane drawer: small, inline, and made the same way for every\n * container type so a tab and an accordion item behave alike.\n */\n function createPaneControls(pane, kind, tools, confirmText, remove) {\n var drawer = prependDrawer(pane, 'ge-tools-drawer ge-pane-drawer');\n\n createMoveTool(drawer);\n addSettingsTool(drawer, pane, settings.pane_classes);\n\n hostTools(drawer, tools);\n\n createTool(drawer, t('tool.delete_pane'), 'ge-delete-pane', 'bi bi-trash', function() {\n deleteNode(kind, pane, confirmText, function(removed) {\n remove(removed);\n });\n });\n\n return drawer;\n }\n\n /**\n * Take a Bootstrap toggle away from a node, and give it back later.\n *\n * Bootstrap binds its data-api handlers on the document in the\n * capture phase, so a listener on the node cannot stop one: the\n * document sees the click first. What does work is leaving nothing\n * for its selector to match, so the attribute is moved aside while\n * the editor needs the control not to react, and moved back on the\n * way out.\n *\n * The attributes are the ones Bootstrap's data api acts on: the tabs',\n * accordions' and popups' toggles and dismisses, and a carousel's\n * slide controls and autoplay.\n */\n var TOGGLE_ATTRIBUTES = ['toggle', 'dismiss', 'slide', 'slide-to', 'ride'];\n\n function suspendToggles(scope) {\n if (!scope) { return; }\n\n dom.selfAndAll(scope, TOGGLE_ATTRIBUTES.map(function(name) { return '[data-bs-' + name + ']'; }).join(', '))\n .forEach(function(node) {\n TOGGLE_ATTRIBUTES.forEach(function(name) {\n var value = node.getAttribute('data-bs-' + name);\n if (value === null) { return; }\n\n node.setAttribute('data-ge-bs-' + name, value);\n node.removeAttribute('data-bs-' + name);\n });\n });\n }\n\n function resumeToggles(scope) {\n if (!scope) { return; }\n\n dom.selfAndAll(scope, TOGGLE_ATTRIBUTES.map(function(name) { return '[data-ge-bs-' + name + ']'; }).join(', '))\n .forEach(function(node) {\n TOGGLE_ATTRIBUTES.forEach(function(name) {\n var value = node.getAttribute('data-ge-bs-' + name);\n if (value === null) { return; }\n\n node.setAttribute('data-bs-' + name, value);\n node.removeAttribute('data-ge-bs-' + name);\n });\n });\n }\n\n /**\n * Rename a label in place. The label sits inside the button Bootstrap\n * toggles from, so the toggle is suspended while the label is being\n * edited: typing in a tab's name must not switch tabs.\n */\n function makeLabelEditable(label) {\n if (editableLabels.has(label)) { return; }\n\n var toggle = dom.closest(label, '[data-bs-toggle], [data-ge-bs-toggle]');\n\n editableLabels.add(label);\n label.setAttribute('title', t('tool.rename'));\n label.addEventListener('dblclick', function(e) {\n e.preventDefault();\n e.stopPropagation();\n\n suspendToggles(toggle);\n label.setAttribute('contenteditable', 'true');\n label.focus();\n window.getSelection().selectAllChildren(label);\n });\n label.addEventListener('keydown', function(e) {\n if (label.getAttribute('contenteditable') !== 'true') { return; }\n\n if (e.key === 'Enter') {\n e.preventDefault();\n label.blur();\n }\n });\n label.addEventListener('blur', function() {\n label.removeAttribute('contenteditable');\n resumeToggles(toggle);\n });\n }\n\n /** The label inside a pane's button, wrapped so it can be edited alone. */\n function labelIn(button) {\n var label = dom.child(button, '.ge-pane-label');\n\n if (!label) {\n label = dom.element('span', { 'class': 'ge-pane-label' }, button.textContent.trim());\n button.innerHTML = '';\n button.appendChild(label);\n }\n\n return label;\n }\n\n function unwrapLabels(scope) {\n dom.all(scope, '.ge-pane-label').forEach(function(label) {\n editableLabels.delete(label);\n dom.unwrap(label);\n });\n }\n\n /**\n * Add a column of `size` to a row, through the add events.\n */\n function addColumnTo(row, size) {\n var column = createColumn(size);\n\n return addNode('column', column, function() {\n row.appendChild(column);\n }, { parent: row, source: 'tool' });\n }\n\n /**\n * Holding the add column tool offers the sizes instead of taking the\n * default one.\n *\n * Held rather than hovered alone, because a hover is a gesture a touch\n * screen does not have, and the tooltip says so: a gesture nobody can\n * see is a gesture nobody finds.\n */\n function attachSizePicker(tool, row) {\n if (!settings.add_column.picker || !tool) { return; }\n\n attachPicker(tool, function() { openSizePicker(tool, row); });\n }\n\n /**\n * Hold a tool - or rest the pointer on it - and `open` offers a\n * choice under it. The add text tool offers its editors the same way.\n */\n function attachPicker(tool, open) {\n var timer = null;\n\n var cancel = function() {\n window.clearTimeout(timer);\n timer = null;\n };\n\n dom.on(tool, 'mouseenter mousedown', function() {\n if (timer || sizePicker) { return; }\n\n timer = window.setTimeout(function() {\n timer = null;\n open();\n }, settings.add_column.delay);\n });\n\n dom.on(tool, 'mouseleave mouseup', cancel);\n }\n\n /**\n * The sizes a column may be given, as a strip under the tool. Sizes\n * that do not fit what is left of the row are marked, not withheld:\n * a row is allowed to wrap, and that is the host's page to lay out.\n */\n function openSizePicker(tool, row) {\n closeSizePicker();\n\n var room = spare(row, leadingTier());\n\n // The drawer it hangs off is raised while it is open: drawers sit\n // below the resize handles, so without this the drawer of the\n // column below takes the clicks meant for the picker\n var drawer = dom.closest(tool, '.ge-tools-drawer');\n if (drawer) { dom.addClass(drawer, 'ge-picker-open'); }\n\n sizePicker = tool.appendChild(dom.element('div', { 'class': 'ge-size-picker' }));\n\n settings.valid_col_sizes.forEach(function(size) {\n var choice = dom.element('a', {\n 'class': 'ge-size',\n 'data-ge-size': size,\n title: sizeTitle(size),\n }, isUnits(size) ? size : sizeClass(BREAKPOINTS[0], size));\n\n dom.toggleClass(choice, 'ge-size-tight', isUnits(size) && size > room);\n dom.toggleClass(choice, 'ge-size-flex', !isUnits(size));\n choice.addEventListener('click', function(e) {\n e.preventDefault();\n e.stopPropagation();\n\n closeSizePicker();\n addColumnTo(row, size);\n });\n sizePicker.appendChild(choice);\n });\n\n // Anywhere else, and the question is withdrawn\n withdrawOnLeave(tool);\n }\n\n function sizeTitle(size) {\n if (size === 'equal') { return t('tool.column_equal'); }\n if (size === 'auto') { return t('tool.column_auto'); }\n\n return t('tool.column_size', { size: size });\n }\n\n /** True when there was one to close, which is also a click's answer. */\n function closeSizePicker() {\n if (!sizePicker) { return false; }\n\n var drawer = dom.closest(sizePicker, '.ge-tools-drawer');\n if (drawer) { dom.removeClass(drawer, 'ge-picker-open'); }\n sizePicker.remove();\n sizePicker = null;\n\n return true;\n }\n\n function createRowControls() {\n dom.all(canvas, '.row').forEach(function(row) {\n if (dom.child(row, '.ge-tools-drawer')) { return; }\n\n var drawer = prependDrawer(row, 'ge-tools-drawer');\n createMoveTool(drawer);\n addSettingsTool(drawer, row, settings.row_classes);\n\n hostTools(drawer, settings.row_tools);\n createTool(drawer, t('tool.delete_row'), 'ge-delete-row', 'bi bi-trash', function() {\n deleteNode('row', row, t('confirm.delete_row'), function(removed) {\n dom.slideUp(row, removed);\n });\n });\n createTool(drawer, t('tool.add_column'), 'ge-add-column', 'bi bi-plus-circle', function() {\n if (closeSizePicker()) { return; } // The picker was open: that was the answer\n\n // In a row with row-cols the new column takes its share\n addColumnTo(row, rowColsSource(row, leadingTier()) ? null : settings.add_column.size);\n });\n\n attachSizePicker(dom.child(drawer, '.ge-add-column'), row);\n\n });\n }\n\n function createColControls() {\n dom.all(canvas, '.column').forEach(function(col) {\n if (dom.child(col, '.ge-tools-drawer')) { return; }\n\n var drawer = prependDrawer(col, 'ge-tools-drawer');\n\n createMoveTool(drawer);\n\n if (settings.resize.tools !== false) {\n createTool(drawer, t('tool.column_narrower'), 'ge-decrease-col-width', 'bi bi-dash-lg', function(e) {\n resizeColumn(col, e.shiftKey\n ? smallest(settings.valid_col_sizes)\n : stepThrough(settings.valid_col_sizes.filter(isUnits), currentUnits(col), -1),\n 'tool');\n });\n\n createTool(drawer, t('tool.column_wider'), 'ge-increase-col-width', 'bi bi-plus-lg', function(e) {\n resizeColumn(col, e.shiftKey\n ? widestFor(col)\n : stepThrough(settings.valid_col_sizes.filter(isUnits), currentUnits(col), 1),\n 'tool');\n });\n }\n\n if (settings.indent.tools !== false) {\n createTool(drawer, t('tool.indent_decrease'), 'ge-decrease-col-offset', 'bi bi-text-indent-right', function(e) {\n indentColumn(col, e.shiftKey\n ? smallest(settings.valid_col_offsets)\n : stepThrough(settings.valid_col_offsets, currentOffset(col), -1),\n 'tool');\n });\n\n createTool(drawer, t('tool.indent_increase'), 'ge-increase-col-offset', 'bi bi-text-indent-left', function(e) {\n indentColumn(col, e.shiftKey ? deepestFor(col) : stepThrough(settings.valid_col_offsets, currentOffset(col), 1), 'tool');\n });\n }\n\n addSettingsTool(drawer, col, settings.col_classes);\n\n hostTools(drawer, settings.col_tools);\n\n createTool(drawer, t('tool.delete_column'), 'ge-delete-column', 'bi bi-trash', function() {\n deleteNode('column', col, t('confirm.delete_column'), function(removed) {\n dom.shrinkAway(col, 400, removed, true);\n });\n });\n\n createTool(drawer, t('tool.add_row'), 'ge-add-row', 'bi bi-plus-circle', function() {\n // An empty row: the columns in it are the next decision,\n // and its drawer's add column tool is where that is made\n var row = createRow();\n\n addNode('row', row, function() {\n col.appendChild(row);\n }, { parent: col, source: 'tool' });\n });\n\n });\n }\n\n /**\n * The tier the tools read when they need one number.\n *\n * In a per-breakpoint view that is the tier being edited. In the all\n * view it is the widest tier, because the canvas is not constrained\n * there and the widest tier is what the user is looking at: clicking\n * \"narrower\" on a column authored as col-lg-6 should take it to 5,\n * not to 11 because no base class was ever written. What the all view\n * writes is the base class all the same.\n */\n function leadingTier() {\n return curView === ALL_VIEW ? BREAKPOINTS[BREAKPOINTS.length - 1] : breakpoint(curView);\n }\n\n /** The size that applies in the view: units, `equal` or `auto`. */\n function currentSize(col) {\n var tier = leadingTier();\n\n // Sized by its row: it has no size of its own to report\n if (rowColsWinner(col, tier)) { return null; }\n\n var size = getEffectiveSize(col, tier);\n return size === null ? MAX_COL_SIZE : size;\n }\n\n /**\n * The size in units, which is what the tools step through. An equal\n * or auto column has no number, so it is measured: the width it has\n * on the canvas, in twelfths of its row.\n */\n function currentUnits(col) {\n var size = currentSize(col);\n if (isUnits(size)) { return size; }\n\n var units = Math.round(dom.outerWidth(col) / rowContentWidth(col.parentElement) * MAX_COL_SIZE);\n return Math.min(Math.max(units, 1), MAX_COL_SIZE);\n }\n\n function rowContentWidth(row) {\n var style = window.getComputedStyle(row);\n\n return row.clientWidth - parseFloat(style.paddingLeft) - parseFloat(style.paddingRight);\n }\n\n function currentOffset(col) {\n return getEffectiveOffset(col, leadingTier()) || 0;\n }\n\n /** The next value a tool moves to, one step along the allowed list. */\n function stepThrough(values, from, direction) {\n var index = values.indexOf(from);\n\n if (index === -1) {\n // A value the host did not allow: step to the nearest one it did\n return values.reduce(function(best, value) {\n return Math.abs(value - from) < Math.abs(best - from) ? value : best;\n }, values[0]);\n }\n\n return values[Math.min(Math.max(index + direction, 0), values.length - 1)];\n }\n\n function smallest(values) {\n return values.filter(isUnits).reduce(function(a, b) { return Math.min(a, b); }, MAX_COL_SIZE);\n }\n\n function largest(values) {\n return values.filter(isUnits).reduce(function(a, b) { return Math.max(a, b); }, 0);\n }\n\n /**\n * The widest this column can be: everything the row has left, minus\n * its own indent. What \"hold shift for max\" means.\n */\n function widestFor(col) {\n var room = spare(col.parentElement, leadingTier(), col) - currentOffset(col);\n\n return Math.min(largest(settings.valid_col_sizes), Math.max(room, 1));\n }\n\n /**\n * The deepest this column can be indented and still have a unit of\n * itself left inside the row.\n */\n function deepestFor(col) {\n var room = spare(col.parentElement, leadingTier(), col) - currentUnits(col);\n\n return Math.min(largest(settings.valid_col_offsets), Math.max(room, 0));\n }\n\n /**\n * The move tool, unless the whole drawer is the handle - in which case\n * a tool that only says \"drag from here\" is one tool too many.\n */\n function createMoveTool(drawer) {\n if (settings.drag_handle === 'drawer') { return null; }\n\n return createTool(drawer, t('tool.move'), 'ge-move', 'bi bi-arrows-move');\n }\n\n /**\n * The drawers that span their node - a row's, a column's, a\n * container's, an element's, a section's - keep their tools to one\n * line. The tools that don't fit are hidden from the end, and a more\n * tool at the drawer's end unfolds it to show them all, wrapping as\n * it would otherwise. They stay where they are, so whatever finds a\n * tool in its drawer, or hangs a picker off it, still does.\n *\n * A text's drawer sits over the text, as wide as its tools, and a\n * pane's sits by its label: neither is one of them.\n */\n var FITTED_DRAWERS = '.ge-tools-drawer:not(.ge-text-drawer):not(.ge-pane-drawer):not(.ge-code-inline)';\n\n /**\n * Fit every drawer as it comes onto the canvas, and again when it\n * changes width or a tool is added to it, shown or hidden. Plugins\n * add tools at their own moments, so this watches rather than\n * waiting to be told.\n */\n function watchDrawers() {\n if (settings.drawer_overflow === 'wrap' || !window.ResizeObserver || !window.MutationObserver) { return; }\n\n var due = new Set();\n var frame = null;\n\n // Once a frame, after the layout: moving tools in the observers'\n // callbacks would resize what they are watching\n function schedule(drawer) {\n due.add(drawer);\n if (frame === null) { frame = window.requestAnimationFrame(flush); }\n }\n\n function flush() {\n frame = null;\n var drawers = Array.from(due);\n due.clear();\n drawers.forEach(function(drawer) {\n if (!drawer.isConnected) {\n drawerResizes.unobserve(drawer);\n return;\n }\n fitDrawer(drawer);\n });\n }\n\n var drawerResizes = new window.ResizeObserver(function(entries) {\n entries.forEach(function(entry) { schedule(entry.target); });\n });\n\n var mutations = new window.MutationObserver(function(records) {\n records.forEach(function(record) {\n var target = record.target;\n\n // A tool shown or hidden\n if (record.type === 'attributes') {\n var parent = target.parentNode;\n if (parent && parent.nodeType === 1 && parent.matches(FITTED_DRAWERS)) { schedule(parent); }\n return;\n }\n\n // A tool added\n if (target.nodeType === 1 && target.matches(FITTED_DRAWERS)) {\n schedule(target);\n return;\n }\n\n record.addedNodes.forEach(function(node) {\n if (node.nodeType !== 1) { return; }\n dom.selfAndAll(node, FITTED_DRAWERS).forEach(function(drawer) {\n dom.addClass(drawer, 'ge-drawer-fit');\n drawerResizes.observe(drawer);\n schedule(drawer);\n });\n });\n });\n });\n mutations.observe(canvas, { childList: true, subtree: true, attributes: true, attributeFilter: ['style'] });\n\n lifetime.signal.addEventListener('abort', function() {\n mutations.disconnect();\n drawerResizes.disconnect();\n if (frame !== null) { window.cancelAnimationFrame(frame); }\n });\n }\n\n /** Hide the tools that don't fit on the drawer's line, from the end, behind its more tool. */\n function fitDrawer(drawer) {\n var tools = dom.children(drawer, 'a').filter(function(tool) { return !dom.hasClass(tool, 'ge-drawer-more'); });\n var expanded = dom.hasClass(drawer, 'ge-drawer-expanded');\n\n // Measured on one line, with every tool back on it\n dom.removeClass(drawer, 'ge-drawer-overflow ge-drawer-expanded');\n tools.forEach(function(tool) { dom.removeClass(tool, 'ge-tool-overflow'); });\n\n if (!drawerOverflows(drawer, tools)) { return; }\n\n dom.addClass(drawer, 'ge-drawer-overflow');\n if (!dom.child(drawer, '.ge-drawer-more')) {\n createTool(drawer, t('tool.more'), 'ge-drawer-more', 'bi bi-three-dots', function() {\n dom.toggleClass(drawer, 'ge-drawer-expanded');\n });\n }\n\n for (var i = tools.length - 1; i >= 0 && drawerOverflows(drawer, tools); i--) {\n dom.addClass(tools[i], 'ge-tool-overflow');\n }\n\n dom.toggleClass(drawer, 'ge-drawer-expanded', expanded);\n }\n\n function drawerOverflows(drawer, tools) {\n var style = window.getComputedStyle(drawer);\n var limit = drawer.getBoundingClientRect().right -\n parseFloat(style.borderRightWidth) - parseFloat(style.paddingRight);\n\n return tools.some(function(tool) {\n var rects = tool.getClientRects();\n return rects.length > 0 && rects[0].right > limit + 0.5;\n });\n }\n\n /**\n * A tool in a drawer: a link with an icon, and what it does. The\n * handlers are a click handler, or { eventName: handler }; each gets\n * the DOM event, with `this` the tool. Hands back the tool.\n */\n function createTool(drawer, title, className, iconClass, eventHandlers) {\n // Through setAttribute rather than spliced into markup: a title is\n // text, and a quote in it - a type name, a host's own title -\n // would end the attribute early\n var tool = dom.element('a', { title: title, 'class': className });\n tool.appendChild(dom.element('i', { 'class': iconClass }));\n drawer.appendChild(tool);\n\n if (typeof eventHandlers == 'function') {\n tool.addEventListener('click', eventHandlers);\n }\n if (eventHandlers && typeof eventHandlers == 'object') {\n Object.keys(eventHandlers).forEach(function(name) {\n dom.on(tool, name, eventHandlers[name]);\n });\n }\n\n return tool;\n }\n\n /**\n * The classes on a node that are the host's own, rather than the ones\n * the grid and the editor put there. What the settings panel shows,\n * and the only ones it is allowed to take away.\n */\n function hostClasses(node) {\n return (node.getAttribute('class') || '').split(/\\s+/).filter(function(name) {\n return name !== '' && !isEditorClass(name);\n });\n }\n\n function isEditorClass(name) {\n if (name === 'row' || name === 'column') { return true; }\n if (/^(ge-|ui-)/.test(name)) { return true; }\n if (/^col(-(sm|md|lg|xl|xxl))?(-auto)?$/.test(name)) { return true; }\n\n return BREAKPOINTS.some(function(tier) {\n return new RegExp('^(' + tier.colPrefix + '|' + tier.offsetPrefix + ')\\\\d+$').test(name);\n });\n }\n\n function setHostClasses(node, value) {\n hostClasses(node).forEach(function(name) { dom.removeClass(node, name); });\n\n value.split(/\\s+/).forEach(function(name) {\n if (name !== '') { dom.addClass(node, name); }\n });\n\n dom.dropEmptyClass(node);\n }\n\n /**\n * The gear and the panel it opens: the node's id, its css classes, and\n * whatever preset toggles the host configured for that kind of node.\n */\n function addSettingsTool(drawer, node, presets) {\n var details = createDetails(node, presets || []);\n detailsFor.set(node, details);\n\n createTool(drawer, t('tool.settings'), 'ge-settings', 'bi bi-gear-fill', function() {\n toggleSettings(node, details, this);\n });\n\n // Beside the gear, because every node that has one is a node a\n // utility may apply to, whichever plugin built its drawer. A\n // feature plugin's tools go there too, for the same reason: the\n // gear is the one tool every drawer has.\n var kind = kindOf(node);\n Object.keys(UTILITIES).forEach(function(name) {\n if (UTILITIES[name].drawerTools) { UTILITIES[name].drawerTools(drawer, node, kind); }\n });\n Object.keys(FEATURES).forEach(function(name) {\n if (FEATURES[name].drawerTools) { FEATURES[name].drawerTools(drawer, node, kind); }\n });\n\n return drawer.appendChild(details);\n }\n\n function createDetails(container, cssClasses) {\n var detailsDiv = dom.element('div', { 'class': 'ge-details' });\n detailsDiv.appendChild(sectionTitle(t('panel.section_general')));\n var general = detailsDiv.appendChild(dom.element('div', { 'class': 'ge-details-general' }));\n var field = function(label) {\n var holder = dom.element('label', { 'class': 'ge-field' });\n holder.appendChild(dom.element('span', { 'class': 'ge-field-label' }, label));\n return general.appendChild(holder);\n };\n\n var id = dom.element('input', {\n 'class': 'ge-id form-control form-control-sm',\n placeholder: t('tool.id_placeholder'),\n title: t('tool.id_title'),\n });\n id.value = container.getAttribute('id') || '';\n field(t('panel.id')).appendChild(id);\n id.addEventListener('change', function() {\n // An empty field means no id, not an empty one\n if (this.value === '') {\n container.removeAttribute('id');\n } else {\n container.setAttribute('id', this.value);\n }\n });\n\n var classes = dom.element('input', {\n 'class': 'ge-classes form-control form-control-sm',\n placeholder: t('tool.classes_placeholder'),\n title: t('tool.classes_title'),\n });\n classes.value = hostClasses(container).join(' ');\n field(t('panel.classes')).appendChild(classes);\n classes.addEventListener('change', function() {\n setHostClasses(container, this.value);\n refreshUtilities(container);\n });\n\n // Bootstrap's outline buttons, filled while their class is on\n var classGroup = general.appendChild(dom.element('div', { 'class': 'btn-group btn-group-sm ge-presets', role: 'group' }));\n cssClasses.forEach(function(rowClass) {\n var on = dom.hasClass(container, rowClass.cssClass);\n var btn = dom.element('a', {\n role: 'button',\n 'class': 'btn btn-sm btn-outline-secondary',\n title: rowClass.title ? rowClass.title : t('tool.toggle_class', { label: rowClass.label }),\n 'aria-pressed': on ? 'true' : 'false',\n });\n\n // A preset's label is the host's markup\n btn.innerHTML = rowClass.label;\n dom.toggleClass(btn, 'active', on);\n btn.addEventListener('click', function() {\n dom.toggleClass(btn, 'active');\n btn.setAttribute('aria-pressed', dom.hasClass(btn, 'active') ? 'true' : 'false');\n dom.toggleClass(container, rowClass.cssClass, dom.hasClass(btn, 'active'));\n refreshUtilities(container);\n });\n classGroup.appendChild(btn);\n });\n\n pluginSections(container).forEach(function(section) { detailsDiv.appendChild(section); });\n\n var utilities = createUtilitiesSection(container);\n if (utilities) { detailsDiv.appendChild(utilities); }\n\n return detailsDiv;\n }\n\n /** The heading of one of a panel's sections. */\n function sectionTitle(text) {\n return dom.element('h6', { 'class': 'ge-section-title' }, text);\n }\n\n /**\n * What plugins add to a node's panel, between its general fields and\n * the Responsive section: each plugin's panelSection(node, kind), in\n * the order they were registered. Where the panel has room - the\n * offcanvas, the modal - the section is in it. A popover or a panel\n * inline in the drawer gets a button instead, and the section opens\n * in the dialog.\n */\n function pluginSections(node) {\n var kind = kindOf(node);\n var mode = panelMode();\n var sections = [];\n\n [CONTAINERS, FEATURES, UTILITIES].forEach(function(registry) {\n Object.keys(registry).forEach(function(name) {\n var plugin = registry[name];\n var section = plugin.panelSection ? plugin.panelSection(node, kind) : null;\n if (!section || !section.body) { return; }\n\n var holder = dom.element('div', { 'class': 'ge-panel-section', 'data-ge-plugin': name });\n\n if (mode === 'offcanvas' || mode === 'modal') {\n holder.appendChild(sectionTitle(t(section.labelKey)));\n holder.appendChild(section.body);\n } else {\n var label = t(section.labelKey);\n var open = holder.appendChild(dom.element('button', {\n type: 'button',\n 'class': 'btn btn-sm btn-outline-secondary ge-panel-section-open',\n }, label));\n\n dom.hide(section.body);\n holder.appendChild(section.body);\n open.addEventListener('click', function() {\n openDialog(section.titleKey ? t(section.titleKey, { kind: kindLabel(node) }) : label,\n section.body, open);\n });\n }\n\n sections.push(holder);\n });\n });\n\n return sections;\n }\n\n /* --------------------------------------------------------------\n * Where a node's settings open.\n *\n * Each node's panel - createDetails' fields, and what plugins add to\n * them - is built into its drawer, as ever. settings_panel says where\n * it shows: 'inline' unfolds it in the drawer; 'offcanvas', 'popover'\n * and 'modal' move it into one of Bootstrap's, outside the canvas,\n * while it is open, and back into its drawer when it closes, so\n * everything that finds a panel through its node keeps working.\n *\n * Bootstrap's markup and styles, but the editor's own opening and\n * placing: a page may load Bootstrap's javascript without Popper, or\n * not at all. The modal is Bootstrap's own when Bootstrap is there.\n * -------------------------------------------------------------- */\n\n var PANEL_MODES = ['offcanvas', 'popover', 'modal', 'inline'];\n var settingsPanels = {}; // One of each, built on first use, outside the canvas\n var openSettingsState = null; // What is open: { mode, node, details, home, next, gear }\n var modalState = new WeakMap(); // modal panel -> { watched, wanted, busy, backdrop, dismissed }\n\n function panelMode() {\n if (PANEL_MODES.indexOf(settings.settings_panel) !== -1) { return settings.settings_panel; }\n\n warnOnceHere('settings_panel', 'settings_panel \"' + settings.settings_panel + '\" is not one of ' +\n PANEL_MODES.join(', ') + ': using offcanvas');\n return 'offcanvas';\n }\n\n /** A node's panel, wherever it is at the moment, or null. */\n function detailsOf(node) {\n return (node && detailsFor.get(node)) || null;\n }\n\n /** Where settings fields are found: the canvas, and the panel open outside it. */\n function settingsScope() {\n return openSettingsState && openSettingsState.mode !== 'inline'\n ? [canvas, openSettingsState.details]\n : [canvas];\n }\n\n /** The gear: its node's panel, opened or closed; another node's closes first. */\n function toggleSettings(node, details, gear) {\n var mode = panelMode();\n\n if (mode === 'inline') {\n dom.toggle(details);\n return;\n }\n\n var same = openSettingsState && openSettingsState.details === details;\n closeSettings();\n if (!same) { openSettings(mode, node, details, gear); }\n }\n\n function openSettings(mode, node, details, gear) {\n var panel = settingsPanel(mode);\n var listening = new AbortController();\n\n openSettingsState = {\n mode: mode,\n node: node,\n details: details,\n home: details.parentElement,\n next: details.nextElementSibling,\n gear: gear,\n listening: listening,\n };\n\n dom.one(panel, '.ge-settings-title').textContent = t('panel.title', { kind: kindLabel(node) });\n dom.one(panel, '.ge-settings-body').appendChild(details);\n dom.show(details);\n dom.addClass(node, 'ge-settings-target');\n\n var signal = { signal: listening.signal };\n document.addEventListener('keydown', function(e) {\n // A dialog over the panel takes the Escape for itself\n if (e.key === 'Escape' && !dialogState) { closeSettings(); }\n }, signal);\n\n if (mode === 'offcanvas') {\n // From the bottom on a phone, from the side anywhere wider\n var narrow = window.innerWidth < 576;\n dom.toggleClass(panel, 'offcanvas-end', !narrow);\n dom.toggleClass(panel, 'offcanvas-bottom', narrow);\n dom.removeClass(panel, 'hiding');\n panel.getBoundingClientRect(); // So the slide in is a transition, not a jump\n dom.addClass(panel, 'show');\n } else if (mode === 'popover') {\n placePopover(panel, gear);\n dom.on(window, 'scroll resize', function() { placePopover(panel, gear); }, signal);\n\n // And again whenever what is in it changes size: the\n // Responsive section unfolding, a plugin swapping a field\n if (window.ResizeObserver) {\n openSettingsState.observer = new window.ResizeObserver(function() { placePopover(panel, gear); });\n openSettingsState.observer.observe(details);\n }\n // A press anywhere else puts it away, as a popover does\n dom.on(document, 'mousedown touchstart', function(e) {\n if (!dialogState && !panel.contains(e.target) && !gear.contains(e.target)) { closeSettings(); }\n }, signal);\n } else {\n showModal(panel, function() {\n if (openSettingsState && openSettingsState.mode === 'modal') { closeSettings(); }\n });\n }\n }\n\n /** Put what is open away, and its panel back in its drawer. */\n function closeSettings() {\n // A dialog opened from the panel goes with it\n closeDialog();\n\n var open = openSettingsState;\n if (!open) { return; }\n openSettingsState = null;\n\n var panel = settingsPanels[open.mode];\n open.listening.abort();\n if (open.observer) { open.observer.disconnect(); }\n\n if (open.mode === 'offcanvas') {\n dom.removeClass(panel, 'show');\n dom.addClass(panel, 'hiding');\n window.setTimeout(function() { dom.removeClass(panel, 'hiding'); }, 300);\n } else if (open.mode === 'popover') {\n dom.hide(panel);\n } else {\n hideModal(panel);\n }\n\n dom.removeClass(open.node, 'ge-settings-target');\n open.details.style.removeProperty('display');\n dom.dropEmptyStyle(open.details);\n\n // Where it was in its drawer, if the drawer is still there: a\n // node deleted while its settings were open took it with it\n if (open.home && dom.attached(open.home)) {\n if (open.next && open.next.parentElement === open.home) {\n open.home.insertBefore(open.details, open.next);\n } else {\n open.home.appendChild(open.details);\n }\n } else {\n open.details.remove();\n }\n }\n\n /** Built once per mode, on first use, and taken away by destroy() or setLocale(). */\n function settingsPanel(mode) {\n if (settingsPanels[mode]) { return settingsPanels[mode]; }\n\n var closeButton = function() {\n return dom.element('button', {\n type: 'button',\n 'class': 'btn-close ge-settings-close',\n 'aria-label': t('panel.close'),\n });\n };\n var panel;\n\n if (mode === 'offcanvas') {\n panel = dom.create('<div class=\"offcanvas offcanvas-end ge-settings-panel ge-settings-offcanvas\" tabindex=\"-1\" role=\"dialog\">' +\n '<div class=\"offcanvas-header\"><h5 class=\"offcanvas-title ge-settings-title\"></h5></div>' +\n '<div class=\"offcanvas-body ge-settings-body\"></div>' +\n '</div>');\n dom.one(panel, '.offcanvas-header').appendChild(closeButton());\n } else if (mode === 'popover') {\n panel = dom.create('<div class=\"popover bs-popover-bottom ge-settings-panel ge-settings-popover\" role=\"dialog\">' +\n '<div class=\"popover-arrow\"></div>' +\n '<div class=\"popover-header\"><span class=\"ge-settings-title\"></span></div>' +\n '<div class=\"popover-body ge-settings-body\"></div>' +\n '</div>');\n dom.one(panel, '.popover-header').appendChild(closeButton());\n dom.hide(panel);\n } else {\n panel = dom.create('<div class=\"modal fade ge-settings-panel ge-settings-modal\" tabindex=\"-1\" role=\"dialog\" aria-hidden=\"true\">' +\n '<div class=\"modal-dialog modal-dialog-centered modal-dialog-scrollable\">' +\n '<div class=\"modal-content\">' +\n '<div class=\"modal-header\"><h5 class=\"modal-title ge-settings-title\"></h5></div>' +\n '<div class=\"modal-body ge-settings-body\"></div>' +\n '<div class=\"modal-footer\"></div>' +\n '</div>' +\n '</div>' +\n '</div>');\n dom.one(panel, '.modal-header').appendChild(closeButton());\n dom.one(panel, '.modal-footer').appendChild(dom.element('button', {\n type: 'button',\n 'class': 'btn btn-primary ge-settings-close',\n }, t('panel.done')));\n }\n\n dom.delegate(panel, 'click', '.ge-settings-close', function(e) {\n e.preventDefault();\n closeSettings();\n });\n\n settingsPanels[mode] = document.body.appendChild(panel);\n return panel;\n }\n\n function removeSettingsPanels() {\n closeSettings();\n\n Object.keys(settingsPanels).forEach(function(mode) {\n if (mode === 'modal') {\n retireModal(settingsPanels[mode]);\n } else {\n settingsPanels[mode].remove();\n }\n });\n Object.keys(settingsPanels).forEach(function(mode) { removeBackdrop(settingsPanels[mode]); });\n settingsPanels = {};\n }\n\n /**\n * Under the gear, or over it when there is more room there, inside\n * the window, and no taller than the room it has: past that its body\n * scrolls.\n */\n function placePopover(panel, gear) {\n if (!dom.attached(gear)) { return; }\n\n dom.show(panel);\n\n var tool = gear.getBoundingClientRect();\n var gap = 8;\n var body = dom.child(panel, '.popover-body');\n body.style.removeProperty('max-height');\n var width = dom.outerWidth(panel);\n var height = dom.outerHeight(panel);\n var roomBelow = window.innerHeight - tool.bottom - 2 * gap;\n var roomAbove = tool.top - 2 * gap;\n var below = height <= roomBelow || roomBelow >= roomAbove;\n var room = below ? roomBelow : roomAbove;\n\n if (height > room) {\n dom.css(body, { 'max-height': Math.max(120, room - (height - dom.outerHeight(body))) });\n height = dom.outerHeight(panel);\n }\n\n var top = below ? tool.bottom + gap : tool.top - gap - height;\n var left = Math.max(gap, Math.min(tool.left + tool.width / 2 - 24, window.innerWidth - width - gap));\n\n dom.toggleClass(panel, 'bs-popover-bottom', below);\n dom.toggleClass(panel, 'bs-popover-top', !below);\n dom.css(panel, { top: top + window.pageYOffset, left: left + window.pageXOffset });\n\n // The arrow points at the gear, wherever the popover had to go\n dom.css(dom.child(panel, '.popover-arrow'), {\n left: Math.max(gap, Math.min(tool.left + tool.width / 2 - left - 8, width - 24)),\n });\n }\n\n /**\n * Bootstrap's modal ignores a hide while it is still fading in, and a\n * show while it is fading out, so the editor asks for what it wants\n * and has it done once the running transition ends: a panel closed as\n * it opens - getHtml, a second click - would otherwise stay open, and\n * empty. A hide Bootstrap starts itself, from Escape or the backdrop,\n * calls `dismissed`, as the close button does: the settings modal\n * closes the settings, the dialog closes the dialog.\n *\n * Without Bootstrap's javascript the modal is shown by hand, over a\n * backdrop of the editor's own that dismisses it when clicked.\n */\n function showModal(panel, dismissed) {\n var Modal = modalLibrary();\n var state = modalState.get(panel);\n\n if (!state) {\n state = { wanted: null, busy: false, backdrop: null, dismissed: dismissed };\n modalState.set(panel, state);\n }\n state.dismissed = dismissed;\n\n if (!Modal) {\n if (!state.backdrop) {\n state.backdrop = dom.element('div', { 'class': 'modal-backdrop fade show ge-settings-backdrop' });\n state.backdrop.addEventListener('click', function() { state.dismissed(); });\n document.body.appendChild(state.backdrop);\n }\n dom.addClass(panel, 'show');\n panel.style.display = 'block';\n panel.removeAttribute('aria-hidden');\n return;\n }\n\n var modal = Modal.getOrCreateInstance(panel);\n\n if (!state.watched) {\n state.watched = true;\n trackModal(panel);\n\n panel.addEventListener('hide.bs.modal', function() {\n // Not asked for: Escape or the backdrop\n if (state.wanted === 'open') {\n state.wanted = 'closed';\n state.busy = true;\n }\n });\n panel.addEventListener('shown.bs.modal', function() {\n state.busy = false;\n if (state.wanted === 'closed') { hideModal(panel); }\n });\n panel.addEventListener('hidden.bs.modal', function() {\n state.busy = false;\n if (state.wanted === 'open') {\n showModal(panel, state.dismissed);\n } else {\n state.dismissed();\n }\n });\n }\n\n state.wanted = 'open';\n if (!state.busy) {\n state.busy = true;\n modal.show();\n }\n }\n\n function hideModal(panel) {\n var Modal = modalLibrary();\n var state = modalState.get(panel);\n\n if (!state) { return; }\n state.wanted = 'closed';\n\n if (!Modal) {\n if (state.backdrop) { state.backdrop.remove(); state.backdrop = null; }\n dom.removeClass(panel, 'show');\n panel.style.removeProperty('display');\n panel.setAttribute('aria-hidden', 'true');\n return;\n }\n\n // Already out of sight - Bootstrap hid it itself, and this is its\n // hidden event closing the settings - and nothing is under way:\n // a hide now would be ignored, and no event would come to say so\n if (!state.busy && dom.hasClass(panel, 'show')) {\n state.busy = true;\n Modal.getOrCreateInstance(panel).hide();\n }\n }\n\n /** A modal's hand made backdrop goes with it. */\n function removeBackdrop(panel) {\n var state = modalState.get(panel);\n if (state && state.backdrop) { state.backdrop.remove(); state.backdrop = null; }\n }\n\n /* --------------------------------------------------------------\n * The dialog: a modal of the editor's own, over whatever settings\n * panel is open, for what does not fit in one. A plugin's section\n * of the panel opens in it when the panel is a popover or inline,\n * and a plugin can open one itself through ge.openDialog.\n *\n * What it shows is borrowed: the body goes into the dialog when it\n * opens and back where it was when it closes, so everything that\n * finds it through its node keeps working. One per editor, built\n * on first use, outside the canvas.\n * -------------------------------------------------------------- */\n\n var dialogPanel = null;\n var dialogState = null; // What is open: { body, home, next, opener, listening }\n\n function dialog() {\n if (dialogPanel) { return dialogPanel; }\n\n dialogPanel = dom.create('<div class=\"modal fade ge-dialog\" tabindex=\"-1\" role=\"dialog\" aria-hidden=\"true\">' +\n '<div class=\"modal-dialog modal-dialog-centered modal-dialog-scrollable\">' +\n '<div class=\"modal-content\">' +\n '<div class=\"modal-header\"><h5 class=\"modal-title ge-dialog-title\"></h5></div>' +\n '<div class=\"modal-body ge-dialog-body\"></div>' +\n '<div class=\"modal-footer\"></div>' +\n '</div>' +\n '</div>' +\n '</div>');\n dom.one(dialogPanel, '.modal-header').appendChild(dom.element('button', {\n type: 'button',\n 'class': 'btn-close ge-dialog-close',\n 'aria-label': t('panel.close'),\n }));\n dom.one(dialogPanel, '.modal-footer').appendChild(dom.element('button', {\n type: 'button',\n 'class': 'btn btn-primary ge-dialog-close',\n }, t('panel.done')));\n\n dom.delegate(dialogPanel, 'click', '.ge-dialog-close', function(e) {\n e.preventDefault();\n closeDialog();\n });\n\n return document.body.appendChild(dialogPanel);\n }\n\n /**\n * ge.openDialog(title, body, opener): show `body` in the dialog. One\n * already open closes first. `opener`, when given, has the focus back\n * when it closes.\n */\n function openDialog(title, body, opener) {\n closeDialog();\n\n var panel = dialog();\n var listening = new AbortController();\n\n dialogState = {\n body: body,\n home: body.parentElement,\n next: body.nextElementSibling,\n opener: opener || document.activeElement,\n listening: listening,\n };\n\n dom.one(panel, '.ge-dialog-title').textContent = title;\n dom.one(panel, '.ge-dialog-body').appendChild(body);\n dom.show(body);\n\n // Bootstrap's modal takes its own Escape; a hand made one does not\n if (!modalLibrary()) {\n document.addEventListener('keydown', function(e) {\n if (e.key === 'Escape') { closeDialog(); }\n }, { signal: listening.signal });\n }\n\n // Bootstrap puts a popover over a modal: the panel the dialog was\n // opened from goes under its backdrop while it is up\n Object.keys(settingsPanels).forEach(function(mode) {\n dom.addClass(settingsPanels[mode], 'ge-under-dialog');\n });\n\n showModal(panel, function() { closeDialog(); });\n }\n\n /** ge.closeDialog(): put the dialog away, and what it showed back where it was. */\n function closeDialog() {\n var open = dialogState;\n if (!open) { return; }\n dialogState = null;\n\n open.listening.abort();\n hideModal(dialogPanel);\n Object.keys(settingsPanels).forEach(function(mode) {\n dom.removeClass(settingsPanels[mode], 'ge-under-dialog');\n });\n\n dom.hide(open.body);\n if (open.home && dom.attached(open.home)) {\n if (open.next && open.next.parentElement === open.home) {\n open.home.insertBefore(open.body, open.next);\n } else {\n open.home.appendChild(open.body);\n }\n } else {\n open.body.remove();\n }\n\n if (open.opener && dom.attached(open.opener) && open.opener.focus) { open.opener.focus(); }\n }\n\n function removeDialog() {\n closeDialog();\n if (!dialogPanel) { return; }\n\n removeBackdrop(dialogPanel);\n retireModal(dialogPanel);\n dialogPanel = null;\n }\n\n /** What a panel's title calls a node. */\n function kindLabel(node) {\n var kind = kindOf(node);\n\n if (CONTAINERS[kind] && CONTAINERS[kind].labelKey) { return t(CONTAINERS[kind].labelKey); }\n\n var paneLabel = Object.keys(CONTAINERS).filter(function(type) {\n return CONTAINERS[type].paneKind === kind && CONTAINERS[type].paneLabelKey;\n })[0];\n if (paneLabel) { return t(CONTAINERS[paneLabel].paneLabelKey); }\n\n switch (kind) {\n case 'row': return t('panel.kind_row');\n case 'column': return t('panel.kind_column');\n case 'text': return t('panel.kind_text');\n case 'element': return t('panel.kind_element');\n case 'section': return t('panel.kind_section');\n case 'tab': return t('panel.kind_tab');\n case 'accordion-item': return t('panel.kind_accordion_item');\n default: return kind;\n }\n }\n\n /**\n * Make sure every column is marked as one, and that a column with no\n * sizing at all gets some.\n *\n * Deliberately conservative: a column that carries any size class is\n * left exactly as authored. Seeding every tier would put six classes\n * on every column now that there are six tiers, and the smallest tier\n * already applies to the wider ones, so one class is enough for a\n * column that had none.\n */\n function addAllColClasses() {\n dom.all(canvas, '.column, div[class*=\"col-\"], div.col').forEach(function(col) {\n dom.addClass(col, 'column');\n\n // A column in a row with row-cols is sized by its row\n if (sizedTiers(col).length || hasRowCols(col.parentElement)) { return; }\n\n setSize(col, BREAKPOINTS[0], MAX_COL_SIZE);\n });\n }\n\n /* --------------------------------------------------------------\n * Columns per row: row-cols-*.\n *\n * A row's row-cols class gives every child an equal share of a\n * line, and a column's own size class takes that share's place.\n * Which of the two wins at a breakpoint is settled the way\n * Bootstrap's css settles it: the class from the wider breakpoint,\n * and at one breakpoint col loses to row-cols, which loses to\n * col-auto and col-N - the order Bootstrap writes their rules in.\n * -------------------------------------------------------------- */\n\n function hasRowCols(row) {\n return dom.hasClass(row, 'row') && BREAKPOINTS.some(function(tier) {\n return ROW_COLS_VALUES.some(function(value) { return dom.hasClass(row, rowColsClass(tier, value)); });\n });\n }\n\n /** The row-cols class that applies to a row at a tier, as { tier, value }, or null. */\n function rowColsSource(row, tier) {\n if (!dom.hasClass(row, 'row')) { return null; }\n\n for (var i = BREAKPOINTS.indexOf(tier); i >= 0; i--) {\n for (var v = 0; v < ROW_COLS_VALUES.length; v++) {\n if (dom.hasClass(row, rowColsClass(BREAKPOINTS[i], ROW_COLS_VALUES[v]))) {\n return { tier: i, value: ROW_COLS_VALUES[v] };\n }\n }\n }\n\n return null;\n }\n\n /** The column's own size that applies at a tier, as { tier, size }, or null. */\n function columnSource(col, tier) {\n for (var i = BREAKPOINTS.indexOf(tier); i >= 0; i--) {\n var size = getSize(col, BREAKPOINTS[i]);\n if (size !== null) { return { tier: i, size: size }; }\n }\n\n return null;\n }\n\n /**\n * The row-cols class that sizes this column at a tier, or null when\n * the column's own size does.\n */\n function rowColsWinner(col, tier) {\n var row = rowColsSource(col.parentElement, tier);\n if (!row) { return null; }\n\n var own = columnSource(col, tier);\n if (!own || row.tier > own.tier) { return row; }\n\n return row.tier === own.tier && own.size === 'equal' ? row : null;\n }\n\n /** A column's share of a line when its row sizes it, in units: auto has no number. */\n function rowColsUnits(winner) {\n return winner.value === 'auto' ? 0 : MAX_COL_SIZE / parseInt(winner.value, 10);\n }\n\n /**\n * What a breakpoint view shows of the row-cols a column is under. The\n * view narrows the canvas, not the window, and Bootstrap's\n * .row-cols-md-3 > * answers to the window - and to nothing the\n * preview can put on the row, since it styles the row's children.\n */\n function rowColsPreview(col, tier) {\n var winner = rowColsWinner(col, tier);\n\n if (winner) {\n return {\n flex: '0 0 auto',\n width: winner.value === 'auto' ? 'auto' : (100 / parseInt(winner.value, 10)) + '%',\n 'max-width': '100%',\n };\n }\n\n // A wider breakpoint's row-cols is live in a wide window; a\n // column with no size of its own here is a full width one\n if (hasRowCols(col.parentElement) && !columnSource(col, tier)) {\n return { flex: '0 0 auto', width: '100%', 'max-width': '100%' };\n }\n\n return {};\n }\n\n /**\n * The badge on a row whose columns are sized by row-cols in the view,\n * and in the all view by its row-cols with no breakpoint.\n */\n function markRowCols(scope) {\n dom.selfAndAll(scope, '.row').forEach(function(row) {\n var source = settings.row_cols === false ? null : (curView === ALL_VIEW\n ? (rowColsSource(row, BREAKPOINTS[0]) || null)\n : rowColsSource(row, breakpoint(curView)));\n\n if (!source) {\n row.removeAttribute('data-ge-row-cols');\n } else {\n row.setAttribute('data-ge-row-cols', rowColsLabel(source.value));\n }\n });\n }\n\n function rowColsLabel(value) {\n return value === 'auto' ? t('badge.row_cols_auto') : t('badge.row_cols', { count: value });\n }\n\n /** The core's family for the field in a row's panel. */\n function rowColsFamily() {\n return {\n name: 'row-cols',\n prefix: 'row-cols',\n values: ROW_COLS_VALUES,\n appliesTo: ['row'],\n labelKey: 'utility.row_cols',\n };\n }\n\n /* --------------------------------------------------------------\n * The sizing core.\n *\n * Everything that reads or writes a size or an offset class goes\n * through here: the width and indent tools, drag resize,\n * createColumn and the getHtml cleanup. One place owns the class\n * names, the 12 unit budget and what an absent class means.\n * -------------------------------------------------------------- */\n\n /**\n * A column's size at one tier: a number of units, `equal`, `auto`, or\n * null when that tier says nothing.\n */\n function getSize(col, tier) {\n var units = readUnits(col, tier.colPrefix);\n if (units !== null) { return units; }\n\n if (dom.hasClass(col, sizeClass(tier, 'auto'))) { return 'auto'; }\n if (dom.hasClass(col, sizeClass(tier, 'equal'))) { return 'equal'; }\n\n return null;\n }\n\n /** The units a column is indented by at one tier, or null. */\n function getOffset(col, tier) {\n return readUnits(col, tier.offsetPrefix);\n }\n\n /**\n * What actually applies at a tier: its own class, or the nearest\n * smaller tier that has one, because that is how Bootstrap cascades.\n * Null when no tier below it says anything either.\n *\n * Not a \"return the first thing I found\" fallback: it walks the tiers\n * downward from the one asked about, so an offset lookup can never\n * answer with a size, and a lookup for one tier can never answer with\n * a wider tier's value.\n */\n function getEffectiveSize(col, tier) {\n return readEffective(col, tier, getSize);\n }\n\n function getEffectiveOffset(col, tier) {\n return readEffective(col, tier, getOffset);\n }\n\n function readEffective(col, tier, read) {\n for (var i = BREAKPOINTS.indexOf(tier); i >= 0; i--) {\n var units = read(col, BREAKPOINTS[i]);\n if (units !== null) { return units; }\n }\n\n return null;\n }\n\n function readUnits(col, prefix) {\n var match = new RegExp('(?:^|\\\\s)' + prefix + '(\\\\d+)(?:\\\\s|$)').exec(col.getAttribute('class') || '');\n return match ? parseInt(match[1], 10) : null;\n }\n\n function writeUnits(col, prefix, units) {\n var classes = (col.getAttribute('class') || '').split(/\\s+/).filter(function(name) {\n return name !== '' && !new RegExp('^' + prefix + '\\\\d+$').test(name);\n });\n\n if (units !== null) { classes.push(prefix + units); }\n\n col.setAttribute('class', classes.join(' '));\n }\n\n /** One size per tier: writing a size takes whatever size the tier had off. */\n function setSize(col, tier, size) {\n writeUnits(col, tier.colPrefix, null);\n FLEX_SIZES.forEach(function(flex) { dom.removeClass(col, sizeClass(tier, flex)); });\n\n if (size !== null && size !== undefined) { dom.addClass(col, sizeClass(tier, size)); }\n }\n\n /** An offset of 0 is written as no class at all, which is what it means. */\n function setOffset(col, tier, units) {\n writeUnits(col, tier.offsetPrefix, units ? units : null);\n }\n\n /** The tiers a column carries an explicit size for. */\n function sizedTiers(col) {\n return BREAKPOINTS.filter(function(tier) {\n return getSize(col, tier) !== null;\n });\n }\n\n /**\n * The units left in a row at one tier, counting every sibling's size\n * and offset. What \"hold shift for max\" grows into.\n */\n function spare(row, tier, ignore) {\n var used = 0;\n\n dom.children(row, '.column').forEach(function(sibling) {\n if (ignore && sibling === ignore) { return; }\n\n // An equal or auto column takes what is left, so it uses none;\n // one its row sizes uses its share of the line\n var winner = rowColsWinner(sibling, tier);\n var size = winner ? rowColsUnits(winner) : getEffectiveSize(sibling, tier);\n used += (isUnits(size) ? size : 0) + (getEffectiveOffset(sibling, tier) || 0);\n });\n\n return MAX_COL_SIZE - used;\n }\n\n /**\n * The 12 unit budget, in one place: a column's size plus its offset\n * never exceeds 12 at any tier.\n *\n * Which of the two gives way is the caller's decision, expressed by\n * which one it marks as leading. Growing an offset shrinks the column;\n * growing a column with no room left is refused, so the tool visibly\n * does nothing rather than quietly rewriting an offset the user set.\n */\n function clamp(request) {\n var size = request.size === null || request.size === undefined ? null : request.size;\n var offset = request.offset === null || request.offset === undefined ? 0 : request.offset;\n\n offset = Math.min(Math.max(offset, 0), MAX_COL_OFFSET);\n\n if (size === null || !isUnits(size)) { return { size: size, offset: offset, refused: false }; }\n\n size = Math.min(Math.max(size, 1), MAX_COL_SIZE);\n\n if (size + offset <= MAX_COL_SIZE) {\n return { size: size, offset: offset, refused: false };\n }\n\n if (request.leading === 'offset') {\n return { size: MAX_COL_SIZE - offset, offset: offset, refused: false };\n }\n\n return { size: null, offset: offset, refused: true };\n }\n\n /**\n * Drag resize leaves an inline pixel width behind: the column follows\n * the pointer in pixels while the gesture lasts. It does not belong in\n * the markup a host saves, or in the canvas once the size class has\n * been written.\n */\n function stripPixelWidths(scope) {\n dom.selfAndAll(scope, '.column').forEach(function(col) {\n dom.css(col, { width: '', height: '', left: '', top: '' });\n\n // Clearing the last property leaves style=\"\" behind, which is\n // an editor leftover like any other\n dom.dropEmptyStyle(col);\n });\n }\n\n /**\n * A group name, scoped to this editor.\n *\n * Two editors on one page must not drag into each other, since a node\n * carries its drawer - and the events that go with it - from the\n * editor that made it.\n */\n function groupName(name) {\n return 'ge-' + name + '-' + instanceId;\n }\n\n /**\n * What the canvas, the columns and the plugins' regions move: rows,\n * text blocks and containers, and whatever blocks a feature adds -\n * the sections plugin's sections. A content area is a block through\n * the text block around it while editing, and on its own before.\n */\n function blockSelector() {\n return ['.row', '.ge-text-block', '.ge-content', '[data-ge-container]']\n .concat(pluginHooks('blocks')).join(', ');\n }\n\n /** A selector every feature plugin may contribute to, under one name. */\n function pluginHooks(name) {\n return Object.keys(FEATURES).map(function(key) {\n return FEATURES[key][name] || null;\n }).filter(function(hook) { return hook !== null; });\n }\n\n /**\n * Whether a region will have a block dropped in it. Every block goes\n * everywhere unless a feature says otherwise: a section only on the\n * canvas, and only rows in a section.\n */\n function acceptsBlock(region, node) {\n var accepted = true;\n\n Object.keys(FEATURES).forEach(function(name) {\n var feature = FEATURES[name];\n if (accepted && feature.accepts && feature.accepts(region, node) === false) { accepted = false; }\n });\n\n return accepted;\n }\n\n /** What must never start a drag, whatever the handle is. */\n function dragCancelSelector() {\n return settings.drag_handle === 'drawer'\n // With the whole drawer as the handle, the tools inside it are\n // still tools: a drag starting on one would swallow its click,\n // and the settings panel has fields to type in\n // - the info tools excepted, which do nothing when clicked:\n // a text's drawer is small and made of little but tools, and\n // with those turned away as well there was nothing to hold\n ? '.ge-tools-drawer > a:not(.ge-text-info):not(.ge-element-info), .ge-details, ' +\n 'input, textarea, button, select, option'\n : 'input, textarea, button, select, option';\n }\n\n /**\n * Every sortable list the editor makes, core's and a plugin's alike,\n * is made here.\n *\n * A caller says what moves (`draggable`) and what the list connects to\n * (`group`, or none for a list that sorts only within itself); the\n * handle, the filter, the callbacks and the drag settings are this\n * function's business. That is the whole point of it: the toolkit\n * underneath is named in one place, so replacing it is one function\n * and not thirty call sites.\n *\n * `lists` is an element or an array of them; `options.accepts`, when\n * given, is asked (list, item) with elements.\n */\n function sortable(lists, options) {\n var Sortable = sortableLibrary();\n\n lists = Array.isArray(lists) ? lists : (lists ? [lists] : []);\n if (!lists.length || !Sortable) { return; }\n\n var wholeDrawer = settings.drag_handle === 'drawer';\n var cancel = dragCancelSelector();\n var soloGroup = 0;\n\n lists.forEach(function(list) {\n // A list with no group sorts only within itself, which is what\n // a tab strip wants: a name of its own, closed both ways\n var group = options.group\n ? { name: groupName(options.group) }\n : { name: groupName(options.draggable + '-' + (++soloGroup)), pull: false, put: false };\n\n // A list may turn some of its group's items away. A put\n // function replaces SortableJS's own test that the item comes\n // from the same group, so it makes that test too: without it\n // a column would drop into the canvas, or into another editor\n if (options.group && options.accepts) {\n group.put = function(to, from, dragged) {\n return from.options.group.name === group.name && options.accepts(to.el, dragged);\n };\n }\n\n sortables.push(Sortable.create(list, Object.assign({\n group: group,\n draggable: options.draggable,\n handle: wholeDrawer ? '.ge-tools-drawer' : '.ge-tools-drawer .ge-move',\n\n /**\n * Two refusals in one, because SortableJS asks once.\n *\n * A tool or a form field never starts a drag, as the\n * cancel list said before. And only a direct child of\n * this list moves: the selector is matched against every\n * descendant, so without this the canvas would pick up a\n * row nested three columns down and drag that.\n */\n filter: function(e, item) {\n if (dom.closest(e.target, cancel, list)) { return true; }\n\n return !item || item.parentNode !== list;\n },\n\n // A filtered pointerdown is still a click on a tool\n preventOnFilter: false,\n\n // The HTML5 drag and drop API cannot be driven by\n // synthetic events, so the tests could not exist without\n // this; it also gives one helper across browsers\n forceFallback: true,\n\n // The copy that follows the pointer is appended to the\n // list the drag started in rather than to the body: it is\n // positioned fixed either way, and inside the canvas it\n // looks like what it is a copy of. On the body none of the\n // editing styles reached it - its drawers came out\n // unstyled, their settings panels open.\n fallbackOnBody: false,\n\n ghostClass: 'ge-drag-placeholder',\n chosenClass: 'ge-drag-chosen',\n dragClass: 'ge-drag-helper',\n fallbackClass: 'ge-drag-helper',\n\n animation: settings.drag.animation,\n\n // One delay, which applies to both gestures or to touch\n // alone: a touch drag that starts instantly takes the\n // page's scrolling with it, a mouse drag has no such\n // problem, and asking for `delay` means asking for both\n delay: settings.drag.delay || settings.drag.touch_delay,\n delayOnTouchOnly: !settings.drag.delay,\n\n touchStartThreshold: settings.drag.threshold,\n scroll: settings.drag.scroll,\n\n onStart: sortStart,\n onEnd: sortEnd,\n }, options.options || {})));\n });\n }\n\n function makeSortable() {\n if (!sortableLibrary()) {\n warnOnceHere('sortable_missing', t('error.sortable_missing'));\n return;\n }\n\n sortable(dom.all(canvas, '.row'), {\n draggable: '.column',\n group: 'column',\n });\n\n sortable([canvas].concat(dom.all(canvas, '.column')), {\n draggable: blockSelector(),\n group: 'block',\n accepts: acceptsBlock,\n });\n\n // A plugin's region can be a block itself - a section is both -\n // and SortableJS tests a list's own element against the draggable\n // selector when it counts the list's children, so every child of\n // a section would count as a block, its drawer first. '>' is\n // SortableJS for \"direct children only\", which the list is not.\n var regions = pluginHooks('regions');\n if (regions.length) {\n sortable(dom.all(canvas, regions.join(', ')), {\n draggable: '>' + blockSelector(),\n group: 'block',\n accepts: acceptsBlock,\n });\n }\n\n // A plugin makes its own: only it knows which of its parts move\n plugins('onSortable', sortable);\n }\n\n /**\n * A drag cannot be refused once it has started, so a canceled\n * before-move is remembered here and undone on drop (spec 2.4). The\n * node carries the mark, because with connected lists the drop is not\n * always reported by the list that started the drag.\n */\n function sortStart(e) {\n var node = e.item;\n var from = positionOf(node);\n var subject = moveSubject(node);\n var move = { from: from, canceled: false };\n\n moves.set(node, move);\n\n operate(function() {\n var moving = emit('before-move', payloadFor(subject.kind, subject.node, {\n parent: from.parent,\n source: 'dragdrop',\n from: from,\n }));\n\n if (!moving) { move.canceled = true; }\n });\n }\n\n /**\n * What a drag reports as moving. A text block is the editor's own\n * wrapper, so what moved is the content area inside it.\n */\n function moveSubject(item) {\n var node = dom.hasClass(item, 'ge-text-block') ? (dom.child(item, '.ge-content') || item) : item;\n\n return { kind: kindOf(node), node: node };\n }\n\n /** Put a node back where a refused drag found it. */\n function putBack(node, from) {\n var siblings = dom.children(from.parent).filter(function(child) {\n return child !== node && !dom.hasClass(child, 'ge-tools-drawer');\n });\n\n if (!siblings.length || from.index >= siblings.length) {\n from.parent.appendChild(node);\n } else {\n from.parent.insertBefore(node, siblings[from.index]);\n }\n }\n\n function sortEnd(e) {\n var node = e.item;\n var move = moves.get(node);\n var from = move ? move.from : positionOf(node);\n\n moves.delete(node);\n\n if (move && move.canceled) {\n putBack(node, from);\n return;\n }\n\n var to = positionOf(node);\n if (to.parent === from.parent && to.index === from.index) {\n return; // A drag that went nowhere is not a move\n }\n\n var container = dom.closest(node, '[data-ge-container]');\n var definition = CONTAINERS[containerTypeOf(container)];\n if (definition && definition.afterPaneMove) {\n definition.afterPaneMove(container, node, from);\n }\n\n // No init() here, unlike an add: the node brought its drawer\n // with it, and the drag is still being finished, so this is the\n // wrong moment to rebuild the lists it is using.\n var subject = moveSubject(node);\n\n operate(function() {\n emit('after-move', payloadFor(subject.kind, subject.node, {\n parent: to.parent,\n source: 'dragdrop',\n from: from,\n to: to,\n container: container || undefined,\n }));\n });\n }\n\n /**\n * Resizing a column by dragging its edge.\n *\n * The handle sits on the column's edge and the sort handle is the\n * drawer, so the two gestures never fight over the same pixels. The\n * column follows the pointer in pixels while dragging, the drawer says\n * which class it would land on, and the pixels are snapped to whole\n * units and thrown away on drop.\n */\n function makeResizable() {\n if (!settings.resize.enabled) { return; }\n\n dom.all(canvas, '.column').forEach(function(col) {\n if (dom.child(col, '.ge-resize-handle')) { return; }\n\n var drawer = dom.child(col, '.ge-tools-drawer');\n if (drawer) { drawer.appendChild(dom.element('span', { 'class': 'ge-resize-size' })); }\n\n resizeEdges().forEach(function(edge) {\n var handle = dom.element('span', {\n 'class': 'ge-resize-handle ge-resize-' + edge,\n 'data-ge-edge': edge,\n });\n handle.addEventListener('pointerdown', startResizeDrag);\n col.appendChild(handle);\n });\n });\n }\n\n /** Which edges carry a handle: 'e', 'w', or both. */\n function resizeEdges() {\n return String(settings.resize.handles).split(',')\n .map(function(edge) { return edge.trim(); })\n .filter(function(edge) { return edge === 'e' || edge === 'w'; });\n }\n\n /**\n * One resize gesture, from the pointer going down on a handle to it\n * coming up again.\n *\n * The pointer is captured, so a fast drag that leaves the column\n * behind keeps resizing it, and a refused before-resize simply never\n * starts: nothing is written and the column does not move.\n */\n function startResizeDrag(e) {\n var handle = e.currentTarget;\n var col = handle.parentElement;\n var west = handle.getAttribute('data-ge-edge') === 'w';\n var startX = e.pageX;\n var startWidth = dom.outerWidth(col);\n\n e.preventDefault();\n\n if (!resizeStart(col)) { return; }\n\n dom.addClass(col, 'ge-resizing');\n if (e.pointerId !== undefined && handle.setPointerCapture) {\n handle.setPointerCapture(e.pointerId);\n }\n\n function widthAt(move) {\n var delta = move.pageX - startX;\n\n return Math.max(1, startWidth + (west ? -delta : delta));\n }\n\n function onMove(move) {\n col.style.width = widthAt(move) + 'px';\n resizeMove(col, widthAt(move));\n }\n\n function onUp(up) {\n handle.removeEventListener('pointermove', onMove);\n dom.off(handle, 'pointerup pointercancel', onUp);\n dom.removeClass(col, 'ge-resizing');\n resizeStop(col, widthAt(up));\n }\n\n handle.addEventListener('pointermove', onMove);\n dom.on(handle, 'pointerup pointercancel', onUp);\n }\n\n function removeResizable() {\n removeResizeFurniture(canvas);\n }\n\n function removeResizeFurniture(root) {\n dom.all(root, '.ge-resize-handle').forEach(function(handle) { handle.remove(); });\n\n dom.all(root, '.ge-resize-size').forEach(function(readout) { readout.remove(); });\n stripPixelWidths(root);\n }\n\n /**\n * The units a pixel width comes to, snapped to whole ones and held\n * inside the same budget the tools obey. With balance 'next' the\n * column may grow into its neighbour, which is what dragging the\n * divider between two columns looks like it should do.\n */\n function snapUnits(col, pixels) {\n var units = Math.round(pixels / rowContentWidth(col.parentElement) * MAX_COL_SIZE);\n var next = balanceSibling(col);\n var nextSize = next ? currentSize(next) : null;\n\n // Measured when the drag started: the column is the width of the\n // pointer now, which is not what it was\n var resize = resizes.get(col);\n var own = resize ? resize.units : currentUnits(col);\n\n // With a sibling to balance against, the drag may take that\n // column's units but not its last one. Without one, the row is\n // allowed to wrap - that is what balance false means - so the only\n // limit is the column's own budget against its indent.\n // An equal or auto sibling gives way by itself, so it sets no limit\n var room = next && isUnits(nextSize)\n ? own + nextSize - smallest(settings.valid_col_sizes)\n : MAX_COL_SIZE - currentOffset(col);\n\n return Math.min(\n Math.max(units, smallest(settings.valid_col_sizes)),\n Math.max(room, smallest(settings.valid_col_sizes)),\n largest(settings.valid_col_sizes)\n );\n }\n\n /** The column that absorbs the delta, when the host asked for that. */\n function balanceSibling(col) {\n if (settings.resize.balance !== 'next') { return null; }\n\n return dom.nextAll(col, '.column')[0] || null;\n }\n\n function resizeReadout(col, text) {\n var drawer = dom.child(col, '.ge-tools-drawer');\n var readout = drawer ? dom.child(drawer, '.ge-resize-size') : null;\n if (readout) { readout.textContent = text; }\n }\n\n function sizeLabel(units) {\n return (curView === ALL_VIEW ? BREAKPOINTS[0].colPrefix : leadingTier().colPrefix) + units;\n }\n\n /**\n * A canceled before-resize refuses the gesture before it begins, so\n * nothing is written and the column does not move. Under jQuery UI\n * this took a flag on the column and a refusal from every step of the\n * drag, because resizable ignores false from its start handler.\n */\n function resizeStart(col) {\n var from = currentSize(col);\n\n var allowed = operate(function() {\n return emit('before-resize', payloadFor('column', col, {\n source: 'dragdrop',\n from: from,\n to: null, // Not known until the pointer stops\n }));\n });\n\n if (!allowed) { return false; }\n\n var resize = { from: from, units: currentUnits(col) };\n resizes.set(col, resize);\n resizeReadout(col, sizeLabel(resize.units));\n\n return true;\n }\n\n function resizeMove(col, width) {\n resizeReadout(col, sizeLabel(snapUnits(col, width)));\n }\n\n function resizeStop(col, width) {\n var resize = resizes.get(col);\n var units = snapUnits(col, width);\n\n resizes.delete(col);\n resizeReadout(col, '');\n stripPixelWidths(col);\n\n if (!resize) { return; }\n\n // A drag of a couple of pixels lands on the size it started from,\n // and is not a resize - not even of an equal or auto column,\n // which it would otherwise turn into a number\n if (units === resize.units) { return; }\n\n var plan = planSize(col, units);\n if (!plan) { return; }\n\n operate(function() {\n writeSize(col, plan);\n balanceAfterResize(col, units - resize.units);\n refreshUtilities(col);\n\n emit('after-resize', payloadFor('column', col, withCleared({\n source: 'dragdrop',\n from: resize.from,\n to: plan.size,\n }, plan.cleared)));\n });\n }\n\n /**\n * The column after takes what the resized one gave or took, unless it\n * is equal or auto: those take what is left by themselves. It is part\n * of the same gesture, so it is not announced separately.\n */\n function balanceAfterResize(col, delta) {\n var next = balanceSibling(col);\n if (!next || !delta) { return; }\n\n var size = currentSize(next);\n if (!isUnits(size)) { return; }\n\n var plan = planSize(next, size - delta);\n if (plan) {\n writeSize(next, plan);\n refreshUtilities(next);\n }\n }\n\n /**\n * Undo every list `sortable()` made, and only those.\n *\n * The registry is what makes that exact: deinit() is a public method,\n * so it can be called twice, and a list the host made sortable itself\n * is none of the editor's business.\n */\n function removeSortable() {\n sortables.forEach(function(sortableInstance) { sortableInstance.destroy(); });\n\n sortables = [];\n }\n\n function createRow() {\n return dom.element('div', { 'class': 'row' });\n }\n\n /**\n * Put a freshly created node where the caller asked for it, through\n * the add events, and bring the canvas up to date so the new markup\n * gets its controls. With no placement option the node stays\n * detached, and placing it and calling reset() is the host's job\n * (spec 1.2).\n *\n * The place is an element, or the first one a selector matches.\n * Returns the node, or null when a handler canceled the add. A call\n * made from inside an event handler is queued, and then returns the\n * node without knowing yet whether the add will be canceled.\n */\n function place(node, kind, options) {\n var placement = null;\n\n PLACEMENTS.forEach(function(name) {\n if (placement === null && options && options[name] !== undefined) {\n placement = name;\n }\n });\n\n if (placement === null) { return node; }\n\n var target = nodeFrom(options[placement]);\n if (!target) {\n warn(kind + ': ' + placement + ' matches no element; the ' + kind + ' is left detached');\n return node;\n }\n\n var parent = (placement === 'appendTo' || placement === 'prependTo')\n ? target\n : target.parentElement;\n\n var add = function() {\n return addNode(kind, node, function() {\n if (placement === 'appendTo') {\n target.appendChild(node);\n } else if (placement === 'prependTo') {\n target.insertBefore(node, target.firstChild);\n } else if (placement === 'insertBefore') {\n target.parentNode.insertBefore(node, target);\n } else {\n dom.insertAfter(node, target);\n }\n }, { parent: parent, source: options.source || 'api' });\n };\n\n if (operationDepth > 0) {\n defer(add);\n return node;\n }\n\n return add();\n }\n\n /**\n * A row, optionally with columns in it: createRow([8, 4]).\n */\n function apiCreateRow(layout, options) {\n var row = createRow();\n\n if (layout !== undefined && !Array.isArray(layout) && !(layout && layout.row_cols)) {\n warn('createRow: the layout is an array of column sizes, as in [8, 4], or ' +\n '{ row_cols, columns }. Making an empty row instead.');\n layout = [];\n }\n\n if (layout && !Array.isArray(layout)) { row = rowFromLayoutValue(layout); }\n\n (Array.isArray(layout) ? layout : []).forEach(function(size) {\n row.appendChild(createColumn(size));\n });\n\n return place(row, 'row', options);\n }\n\n /**\n * A column of `size` units, optionally holding `options.content`.\n */\n function apiCreateColumn(size, options) {\n options = options || {};\n\n // Going into a row with row-cols, no size is a size: the row's share\n var into = nodeFrom(options.appendTo || options.prependTo || null);\n\n if (size === undefined && into && rowColsSource(into, leadingTier())) {\n size = null;\n } else if (!isUnits(size) && FLEX_SIZES.indexOf(size) === -1) {\n warn('createColumn: no column size given, using ' + MAX_COL_SIZE);\n size = MAX_COL_SIZE;\n }\n\n var column = createColumn(size, options.offset);\n if (options.content !== undefined) {\n column.appendChild(contentFor(options.content));\n }\n\n return place(column, 'column', options);\n }\n\n /**\n * A container of the given type, with its panes already in it.\n */\n function apiCreateContainer(type, options) {\n options = options || {};\n\n var definition = CONTAINERS[type];\n if (!definition) {\n warn('createContainer: no such container type \"' + type + '\"');\n return null;\n }\n\n return place(definition.create(options), type, options);\n }\n\n /** A pane appended to a container, through the add events. */\n function addPaneTo(container, type, options) {\n container = nodeFrom(container);\n options = options || {};\n\n var definition = CONTAINERS[containerTypeOf(container)];\n\n if (!definition || containerTypeOf(container) !== type) {\n warn('this is not a ' + type + ' container');\n return null;\n }\n\n var pane = definition.addPane(container, options);\n if (!pane) { return null; }\n\n return addNode(definition.paneKind, pane, function() {}, {\n parent: container,\n source: 'api',\n container: container,\n });\n }\n\n /** A pane appended to a container of any type that has panes. */\n function apiAddPane(container, options) {\n container = nodeFrom(container);\n\n var type = containerTypeOf(container);\n if (!CONTAINERS[type] || !CONTAINERS[type].addPane) {\n warn('addPane: this is not a container with panes');\n return null;\n }\n\n return addPaneTo(container, type, options);\n }\n\n /**\n * A shallow frozen copy of the settings for the instance, so a host\n * can read what the editor is running with without changing it\n * behind the editor's back. Arrays are copied; the objects inside them\n * are the host's own and stay shared.\n */\n function settingsCopy() {\n var copy = {};\n\n Object.keys(settings).forEach(function(key) {\n var value = settings[key];\n copy[key] = Array.isArray(value) ? value.slice() : value;\n });\n\n return Object.freeze(copy);\n }\n\n /**\n * A column sized for the current view: its tier, or the base class in\n * the all view. `offset` indents it, within the same 12 unit budget.\n */\n function createColumn(size, offset) {\n // Empty: what goes in it is the next decision, and the tools of\n // the column and the toolbar are where it is made\n var column = dom.element('div', { 'class': 'column' });\n\n // The tier being edited, or the base class in the all view\n var tier = tiersFor(curView)[0];\n var wanted = clamp({ size: size, offset: offset || 0, leading: 'offset' });\n\n setSize(column, tier, wanted.size === null ? size : wanted.size);\n setOffset(column, tier, wanted.offset);\n\n return column;\n }\n\n /**\n * Run custom content filter on init and deinit. A filter is a\n * function, or the name of one on window, and gets the canvas and\n * whether this is init.\n */\n function runFilter(isInit, root) {\n if (!settings.custom_filter || !settings.custom_filter.length) { return; }\n\n var filters = typeof settings.custom_filter === 'string' || typeof settings.custom_filter === 'function'\n ? [settings.custom_filter]\n : settings.custom_filter;\n\n Array.prototype.forEach.call(filters, function(func) {\n if (typeof func == 'string') {\n func = window[func];\n }\n\n func(root || canvas, isInit);\n });\n }\n\n /**\n * What a text is never made of: rows, containers, and whatever a\n * feature plugin says - the elements plugin's elements. Each is a\n * block of the column's, beside the texts.\n */\n function textCutter() {\n var cuts = ['.row', '[data-ge-container]'];\n\n Object.keys(FEATURES).forEach(function(name) {\n var feature = FEATURES[name];\n var cut = typeof feature.cuts === 'function' ? feature.cuts() : feature.cuts;\n if (cut) { cuts.push(cut); }\n });\n\n return cuts.join(', ');\n }\n\n /**\n * Take the blocks out of the text.\n *\n * Up to 5.x an element lived inside a content area, among the text\n * a rich text editor edited. From 6.0 it is a block of its own, so a\n * content area with one inside - markup 5.x saved - is cut there: the\n * text before stays in the content area, the element goes into the\n * column after it, and the text after goes into a new content area of\n * the same type. Only a content area's own children cut it, which is\n * where 5.x recognized elements; one inside a paragraph is text, as\n * it was. A part with nothing but whitespace is dropped, and the first\n * part that has something keeps the content area, id and classes and\n * all.\n *\n * On every init, and a no-op on markup 6.0 made: nothing to cut. A\n * content area its editor is open on is left for the next init.\n */\n function splitTexts(cutter) {\n dom.all(canvas, '.column > .ge-content, .column > .ge-text-block > .ge-content').forEach(function(area) {\n if (dom.hasClass(area, 'ge-rte-active') || !dom.children(area, cutter).length) { return; }\n\n var type = area.getAttribute('data-ge-content-type');\n var anchor = dom.hasClass(area.parentElement, 'ge-text-block') ? area.parentElement : area;\n var pieces = [];\n var run = [];\n\n Array.prototype.slice.call(area.childNodes).forEach(function(node) {\n if (node.nodeType === 1 && node.matches(cutter)) {\n pieces.push({ text: run }, { block: node });\n run = [];\n } else {\n run.push(node);\n }\n });\n pieces.push({ text: run });\n\n while (area.firstChild) { area.removeChild(area.firstChild); }\n\n var kept = false;\n var last = anchor;\n\n pieces.forEach(function(piece) {\n var placed;\n\n if (piece.block) {\n placed = piece.block;\n } else if (!hasContent(piece.text)) {\n return;\n } else if (kept) {\n // Of the same type, or of none if it had none\n placed = createDefaultContentWrapper(type);\n piece.text.forEach(function(node) { placed.appendChild(node); });\n } else {\n // The content area itself, moved along if an\n // element came before the first text\n piece.text.forEach(function(node) { area.appendChild(node); });\n placed = anchor;\n kept = true;\n }\n\n if (placed !== last) { dom.insertAfter(placed, last); }\n last = placed;\n });\n\n if (!kept) { anchor.remove(); }\n });\n }\n\n /** Whether a run of nodes has anything in it but whitespace. */\n function hasContent(nodes) {\n return nodes.some(function(node) {\n return node.nodeType === 1 || (node.nodeType === 3 && /\\S/.test(node.nodeValue));\n });\n }\n\n /**\n * Wrap column content in <div class=\"ge-content\"> where neccesary\n */\n function wrapContent(cutter) {\n dom.all(canvas, '.column').forEach(function(col) {\n var contents = [];\n\n dom.children(col).forEach(function(child) {\n // The editor's own furniture is not content and not a\n // boundary either. The resize handle used to be treated as\n // content and wrapped into a content area of its own on\n // the next init.\n if (dom.is(child, '.ge-tools-drawer, .ge-resize-handle')) { return; }\n\n // A container, or an element, sits in the column beside\n // the content areas, not inside one, so it ends a run of\n // loose content rather than joining it\n if (dom.is(child, '.ge-content, .ge-text-block') || child.matches(cutter)) {\n contents = doWrap(contents);\n } else {\n contents.push(child);\n }\n });\n\n doWrap(contents);\n });\n }\n\n /**\n * Wrap a run of loose column content in a content area of no type -\n * the host's plain content - and hand back\n * an empty run: the caller has to forget what it just wrapped, or the\n * next boundary wraps the same nodes again and leaves the first\n * wrapper behind, empty.\n */\n function doWrap(contents) {\n if (contents.length) {\n var contentArea = dom.insertAfter(createDefaultContentWrapper(), contents[contents.length - 1]);\n contents.forEach(function(node) { contentArea.appendChild(node); });\n }\n\n return [];\n }\n\n /**\n * A content area of a text type, or with none the host's plain\n * content: a content area and nothing more.\n */\n function createDefaultContentWrapper(type) {\n var contentArea = dom.element('div', { 'class': 'ge-content' });\n\n if (type) {\n dom.addClass(contentArea, 'ge-content-type-' + type);\n contentArea.setAttribute('data-ge-content-type', type);\n }\n\n return contentArea;\n }\n\n /* --------------------------------------------------------------\n * Content blocks: a content area as a block of its own, with a drawer.\n *\n * The drawer cannot go inside the content area, as every other\n * block's does: what is inside may be a text editor's, which would\n * make the drawer editable text, copy it into its own document or\n * take it away on an undo. So while editing, each content area in a\n * column sits in a .ge-text-block beside its drawer, and that wrapper\n * is the block the column moves. deinit takes it off again: it is\n * never part of the markup.\n *\n * A content area with no type is the host's plain content, and its\n * drawer is the editor's: move and delete, nothing else. One whose\n * type a plugin declares is that plugin's text, and the plugin gives\n * it its drawer. One whose type nobody declares is a text whose\n * editor is not loaded: a block to move and delete, not to edit.\n * -------------------------------------------------------------- */\n\n function wrapTexts() {\n dom.all(canvas, '.column > .ge-content').forEach(function(area) {\n dom.wrap(area, dom.element('div', { 'class': 'ge-text-block' }));\n });\n\n dom.all(canvas, '.ge-text-block').forEach(function(textBlock) {\n if (dom.child(textBlock, '.ge-tools-drawer')) { return; }\n\n var area = dom.child(textBlock, '.ge-content');\n var type = area ? area.getAttribute('data-ge-content-type') : null;\n\n if (!type) {\n createPlainControls(textBlock);\n } else if (!hasTextOwner(type)) {\n createOrphanControls(textBlock, type);\n }\n });\n }\n\n /** After the drawers are gone, so a wrapper holds its content area and nothing else. */\n function unwrapTexts(root) {\n dom.all(root, '.ge-text-block').forEach(function(textBlock) {\n dom.unwrap(textBlock);\n });\n }\n\n /** The host's plain content: moved and deleted here, edited in the source. */\n function createPlainControls(textBlock) {\n var block = dom.child(textBlock, '.ge-content');\n var drawer = prependDrawer(textBlock, 'ge-tools-drawer ge-text-drawer ge-plain-drawer');\n dom.addClass(textBlock, 'ge-plain-block');\n\n createMoveTool(drawer);\n\n // The tools a feature plugin gives plain content, which is not\n // every plugin's drawerTools: no gear, no utilities, no copy\n Object.keys(FEATURES).forEach(function(name) {\n if (FEATURES[name].plainTools) { FEATURES[name].plainTools(drawer, block); }\n });\n\n createTool(drawer, t('tool.delete_plain'), 'ge-delete-plain', 'bi bi-trash', function() {\n deleteNode('plain', block, t('confirm.delete_plain'), function(removed) {\n dom.slideUp(textBlock, function() {\n textBlock.remove();\n removed();\n });\n });\n });\n }\n\n /**\n * A text whose editor is not loaded: still a block to move and delete,\n * and its drawer says why it cannot be edited.\n */\n function createOrphanControls(textBlock, type) {\n var block = dom.child(textBlock, '.ge-content');\n var drawer = prependDrawer(textBlock, 'ge-tools-drawer ge-text-drawer');\n\n createMoveTool(drawer);\n createTool(drawer, t('text.no_editor', { type: type }), 'ge-text-info ge-text-missing',\n 'bi bi-exclamation-triangle');\n createTool(drawer, t('tool.delete_text'), 'ge-delete-text', 'bi bi-trash', function() {\n deleteNode('text', block, t('confirm.delete_text'), function(removed) {\n dom.slideUp(textBlock, function() {\n textBlock.remove();\n removed();\n });\n });\n });\n }\n\n /**\n * A detached content area holding `content` - html, or a node - as a\n * text of the first type offered, or the host's plain content when no\n * editor is offered.\n */\n function contentFor(content) {\n var offers = textOffers();\n var area = createDefaultContentWrapper(offers.length ? offers[0].type : null);\n\n if (content && content.nodeType) {\n area.appendChild(content);\n } else {\n dom.setHtml(area, content);\n }\n\n return area;\n }\n\n /**\n * Constrain the canvas to the view's preview width and make that\n * tier's classes the effective ones. The all view constrains nothing:\n * every tier is live, which is how the page will really render.\n */\n function switchLayout(view) {\n curView = view;\n\n VIEW_KEYS.forEach(function(key) {\n dom.toggleClass(canvas, 'ge-layout-' + key, key === view);\n });\n dom.one(layoutDropdown, 'button').textContent = t(labelKeyFor(view));\n }\n\n /** The view key a caller asked for, or null. */\n function viewKey(view) {\n return VIEW_KEYS.indexOf(view) === -1 ? null : view;\n }\n\n function changeView(view) {\n var key = viewKey(view);\n\n if (key === null) {\n warn('changeView(' + JSON.stringify(view) + '): no such layout mode');\n return;\n }\n\n var from = curView;\n switchLayout(key);\n\n if (key === from) { return; }\n\n settingsScope().forEach(function(scope) {\n dom.all(scope, '.ge-utilities').forEach(function(section) { renderUtilities(section); });\n });\n renderPluginFields(null);\n refreshPreviews(canvas);\n plugins('onViewChange', key);\n emit('view-change', { canvas: canvas, breakpoint: key, from: from, to: key });\n }\n\n function getView() {\n return curView;\n }\n\n /** A method a feature plugin contributes, or a warning that the plugin is not loaded. */\n function featureMethod(name, plugin, file) {\n return function() {\n if (!featureMethods[name]) {\n warnOnceHere('plugin:' + plugin, name + ' needs the ' + plugin + ' plugin: ' +\n 'include dist/plugins/grideditor.' + file + '.js after the editor');\n return null;\n }\n\n return featureMethods[name].apply(null, arguments);\n };\n }\n\n /**\n * The instance's own methods: the documented API. init and reset are\n * deferred when a handler calls them, so an operation in flight\n * finishes before the canvas is rebuilt. The ones that do something,\n * rather than answer something, hand back the instance, to chain.\n */\n function apiSetActiveTarget(value) {\n if (!settings.active_target) {\n warnOnceHere('active_target', 'setActiveTarget needs the active_target setting: without it, it does nothing');\n return;\n }\n if (value === null || value === undefined) { changeTarget(null); return; }\n\n var node = nodeFrom(value);\n if (!isTarget(node)) {\n var named = typeof value === 'string' ? value : (node ? '<' + node.tagName.toLowerCase() + '>' : String(value));\n warn('setActiveTarget: ' + named + ' is not a column or a region of the canvas');\n return;\n }\n\n changeTarget(node);\n }\n\n var own = {\n getHtml: getHtml,\n getPlainHtml: getPlainHtml,\n init: function() { defer(init); },\n reset: function() { defer(reset); },\n deinit: deinit,\n destroy: destroy,\n changeView: changeView,\n getView: getView,\n createRow: apiCreateRow,\n createColumn: apiCreateColumn,\n createText: function(type, options) {\n if (!featureMethods.createText) {\n warnOnceHere('plugin:text', 'createText needs a text editor plugin: include ' +\n 'dist/plugins/grideditor.tinymce.js, or another editor\\'s, after the editor');\n return null;\n }\n\n return featureMethods.createText(type, options);\n },\n createElement: featureMethod('createElement', 'elements', 'elements'),\n createSection: featureMethod('createSection', 'sections', 'sections'),\n createContainer: apiCreateContainer,\n addTab: function(container, options) { return addPaneTo(container, 'tabs', options); },\n addAccordionItem: function(container, options) {\n return addPaneTo(container, 'accordion', options);\n },\n addPane: apiAddPane,\n setLocale: setLocale,\n getUtility: getUtility,\n setUtility: setUtility,\n getActiveTarget: function() { return settings.active_target ? activeTarget : null; },\n setActiveTarget: apiSetActiveTarget,\n };\n\n Object.keys(own).forEach(function(name) {\n var value = !!(METHODS[name] && METHODS[name].value);\n\n instance[name] = function() {\n if (destroyed) {\n warnOnceHere('destroyed:' + name, t('warning.destroyed', { method: name }));\n if (name === 'getHtml') { return canvas.innerHTML; }\n if (name === 'getPlainHtml') { return plainHtml(canvas.innerHTML); }\n return value ? null : instance;\n }\n\n var result = own[name].apply(instance, arguments);\n return value ? result : instance;\n };\n });\n\n instance.canvas = canvas;\n instance.settings = settingsCopy();\n\n instances.set(canvas, instance);\n\n loadPlugins();\n // Again, with what the plugins filled in: the text editors'\n // content_types when the host gave none\n instance.settings = settingsCopy();\n\n // A feature plugin's methods that are not the editor's own documented\n // ones - the autosave plugin's - are the instance's too, while the\n // plugin is there\n Object.keys(featureMethods).forEach(function(name) {\n if (Object.prototype.hasOwnProperty.call(own, name) || name in instance) { return; }\n\n instance[name] = function() {\n if (destroyed) {\n warnOnceHere('destroyed:' + name, t('warning.destroyed', { method: name }));\n return null;\n }\n\n return featureMethods[name].apply(null, arguments);\n };\n });\n setup();\n init();\n\n GridEditor._created.forEach(function(hook) { hook(instance); });\n}\n\n/**\n * What a module that builds on the editor - the jQuery adapter - is told:\n * each editor as it is made. Not the plugin contract; a plugin is handed\n * the editor through its factory.\n */\nGridEditor._created = [];\n\n/**\n * Container plugins: tabs, accordions, popups, carousels, cards, and whatever a host writes.\n *\n * A plugin is a factory registered under the type it builds, called once per\n * editor with the handle described in docs/plugins.md. Loading its file is\n * what makes the type available; the `plugins` setting narrows that list.\n *\n * GridEditor.containers.gallery = function(ge) {\n * return { labelKey: ..., create: ..., mark: ..., unmark: ... };\n * };\n */\nGridEditor.containers = {};\n\n/**\n * Feature plugins: a piece of the editor that is not a container type, in a\n * file of its own. Element level controls are one. Same bargain as a\n * container plugin - a factory under its name, called once per editor with\n * the handle in docs/plugins.md - and the same `plugins` setting decides\n * which of the loaded ones are used.\n */\nGridEditor.features = {};\n\n/**\n * Utility plugins: Bootstrap's responsive utility classes - order-md-2,\n * d-lg-none - edited per breakpoint. A plugin declares families of classes\n * and the editor reads them, writes them, puts them in the settings panel and\n * previews them in each view. Same factory, same `plugins` setting.\n *\n * GridEditor.utilities.order = function(ge) {\n * return { families: [{ name: 'order', prefix: 'order', values: [...] }] };\n * };\n */\nGridEditor.utilities = {};\n\n/**\n * The text editors, by the content type each edits: what the text plugins\n * (tinymce, ckeditor, summernote, a host's own) register, and the text\n * feature, src/js/text/grideditor.text.js, reads.\n */\nGridEditor.texts = {};\n\n/** Translator for the plugins, which get settings and no instance. */\nGridEditor.t = translate;\n\n/** getPlainHtml for html that is not on a canvas, for the jQuery adapter. Not the public API. */\nGridEditor._plainHtml = plainHtml;\n\n/**\n * SortableJS and Bootstrap's javascript, for a page that imports them as\n * modules and so has no window.Sortable or window.bootstrap. Looked up\n * before the globals; only Bootstrap's Modal is used.\n */\nGridEditor.Sortable = null;\nGridEditor.bootstrap = null;\n\n/** The version of the build, filled in by build/build.js. */\nGridEditor.version = typeof __GRIDEDITOR_VERSION__ === 'undefined' ? 'dev' : __GRIDEDITOR_VERSION__;\n\n/**\n * Locale registry: code -> { key: string }.\n *\n * English is built in rather than shipped as a file, because it is where every\n * lookup ends: a page that loads no locale file still has a complete UI.\n * Removing a key from it is a breaking change. Locale files register\n * themselves here, see src/js/locales/.\n *\n * Every key is listed in docs/locale-keys.md, which test/locales.js holds to\n * this catalogue in both directions.\n */\nGridEditor.locales = {\n en: {\n 'tool.move': 'Move',\n 'tool.settings': 'Settings',\n 'tool.add_row': 'Add row',\n 'tool.delete_text': 'Remove text',\n 'tool.delete_plain': 'Remove content',\n 'tool.convert_type': 'Edit as {editor} text',\n 'text.no_editor': 'No text editor \"{type}\" is loaded: this text can be moved and deleted, not edited',\n 'tool.add_column': 'Add column\\n(hold to choose the width)',\n 'tool.column_size': '{size} of 12',\n 'tool.column_equal': 'Equal: shares what the row has left',\n 'tool.column_auto': 'Auto: as wide as its content',\n 'tool.delete_row': 'Remove row',\n 'tool.delete_column': 'Remove col',\n 'tool.delete_container': 'Remove container',\n 'tool.delete_pane': 'Remove pane',\n 'tool.rename': 'Double click to rename',\n 'tool.column_narrower': 'Make column narrower\\n(hold shift for min)',\n 'tool.column_wider': 'Make column wider\\n(hold shift for max)',\n 'tool.indent_decrease': 'Decrease indent\\n(hold shift for none)',\n 'tool.indent_increase': 'Increase indent\\n(hold shift for max)',\n 'tool.edit_source': 'Edit Source Code',\n 'tool.preview': 'Preview',\n 'tool.more': 'More',\n 'group.rows': 'Rows',\n 'group.content': 'Content',\n 'group.elements': 'Elements',\n 'group.select': 'Add',\n 'panel.title': '{kind} settings',\n 'panel.close': 'Close',\n 'panel.done': 'Done',\n 'panel.id': 'Id',\n 'panel.classes': 'Classes',\n 'panel.section_general': 'Id and classes',\n 'panel.kind_row': 'Row',\n 'panel.kind_column': 'Column',\n 'panel.kind_element': 'Element',\n 'panel.kind_section': 'Section',\n 'panel.kind_tab': 'Tab',\n 'panel.kind_accordion_item': 'Accordion item',\n 'tool.id_placeholder': 'id',\n 'tool.id_title': 'Set a unique identifier',\n 'tool.classes_placeholder': 'classes',\n 'tool.classes_title': 'Css classes, separated by spaces',\n 'tool.toggle_class': 'Toggle \"{label}\" styling',\n 'row.add': 'Add row {layout}',\n 'row.add_row_cols': 'Add a row of {columns} columns, {counts} per row',\n 'confirm.title': 'Confirm',\n 'confirm.ok': 'Delete',\n 'confirm.cancel': 'Cancel',\n 'confirm.delete_row': 'Delete row?',\n 'confirm.delete_column': 'Delete column?',\n 'confirm.delete_text': 'Delete this text?',\n 'confirm.delete_plain': 'Delete this content?',\n 'confirm.delete_container': 'Delete this container and everything in it?',\n 'view.all': 'All sizes',\n 'view.xs': 'Phone',\n 'view.sm': 'Tablet',\n 'view.md': 'Small desktop',\n 'view.lg': 'Desktop',\n 'view.xl': 'Large desktop',\n 'view.xxl': 'Widescreen',\n 'utility.section': 'Responsive: {view}',\n 'utility.col_width': 'Width',\n 'utility.col_equal': 'Equal',\n 'utility.col_auto': 'Auto',\n 'utility.col_from_row': 'From the row: {count}',\n 'utility.row_cols': 'Columns per row',\n 'badge.row_cols': '{count} per row',\n 'badge.row_cols_auto': 'As wide as their content',\n 'utility.default': 'Default',\n 'utility.inherit': 'Inherit: {value} (from {breakpoint})',\n 'utility.varies': 'Changes at {breakpoints}; choosing here replaces that',\n 'error.sortable_missing': 'SortableJS not available! Make sure you loaded the Sortable js file; dragging is off without it.',\n 'warning.already_editing': 'This element already has an editor: that one is handed back, with the options it was made with.',\n 'warning.destroyed': '{method}() was called on an editor that has been destroyed, and does nothing.',\n 'warning.duplicate_build': 'grideditor.js was loaded twice: the first GridEditor is kept.',\n 'warning.adapter_no_jquery': 'grideditor.jquery.js needs jQuery 4, and there is no jQuery on the page: the jQuery API is not there.',\n 'error.tinymce_missing': 'tinyMCE not available! Make sure you loaded the tinyMCE js file.',\n 'error.ckeditor_missing': 'CKEditor 5 not available! Make sure you loaded its ckeditor5.umd.js file.',\n 'error.summernote_missing': 'Summernote not available! Make sure you loaded jQuery and the Summernote js file.',\n },\n};\n\nexport { GridEditor };\nexport default GridEditor;\n", "/**\n * The classic script's entry: the editor as window.GridEditor, for a page\n * that loads it with a <script> tag and its plugins after it.\n *\n * Loaded twice, the first copy is kept: its plugins registered on it, and\n * the editors on the page are its.\n */\nimport { GridEditor } from './grideditor.js';\n\nif (window.GridEditor) {\n if (window.console && window.console.warn) {\n window.console.warn('grid-editor: ' + GridEditor.t({ locale: 'en' }, 'warning.duplicate_build'));\n }\n} else {\n window.GridEditor = GridEditor;\n}\n"],
|
|
5
|
-
"mappings": "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",
|
|
6
|
-
"names": ["all", "root", "selector", "one", "selfAndAll", "found", "children", "node", "each", "child", "closest", "stopAt", "is", "attached", "nextAll", "next", "parentsUntil", "stop", "parent", "parse", "html", "template", "create", "nodes", "i", "element", "tag", "attributes", "text", "name", "value", "setHtml", "addClass", "names", "split", "removeClass", "toggleClass", "state", "hasClass", "dropEmptyClass", "dropEmptyStyle", "attr", "css", "styles", "property", "UNITLESS", "defaultDisplays", "defaultDisplay", "probe", "show", "hide", "toggle", "visible", "outerWidth", "outerHeight", "contentHeight", "style", "offset", "box", "insertAfter", "node", "reference", "unwrap", "parent", "wrap", "wrapper", "delegate", "root", "types", "selector", "handler", "options", "listener", "event", "match", "closest", "split", "type", "on", "target", "off", "DEFAULT_DURATION", "animateAway", "node", "frames", "duration", "done", "finish", "hide", "visible", "animation", "called", "once", "slideUp", "style", "shrinkAway", "node", "duration", "done", "width", "animateAway", "style", "from", "to", "METHODS", "PLACEMENTS", "BREAKPOINTS", "ALL_VIEW", "ALL_VIEW_LABEL_KEY", "VIEW_KEYS", "tier", "MAX_COL_SIZE", "MAX_COL_OFFSET", "FLEX_SIZES", "ROW_COLS_VALUES", "rowColsClass", "value", "isUnits", "size", "sizeClass", "breakpoint", "key", "i", "tiersFor", "view", "labelKeyFor", "NESTED_SETTINGS", "warned", "editorCounter", "instances", "translate", "settings", "params", "locales", "GridEditor", "locale", "overrides", "string", "warnOnce", "placeholder", "name", "hasString", "warn", "message", "english", "targetElement", "target", "found", "nodeFrom", "node", "sortableLibrary", "modalLibrary", "bootstrap", "plainHtml", "html", "root", "emptied", "all", "marked", "attribute", "classes", "kept", "div", "unwrap", "options", "element", "existing", "doubleWarned", "build", "instance", "baseElem", "optionsOrMethod", "canvas", "mainControls", "wrapper", "addRowGroup", "addContainerGroup", "layoutDropdown", "htmlTextArea", "curView", "confirmDialog", "sizePicker", "sourceOpen", "dropMarker", "activeTarget", "toolbarLifetime", "closeOverflowMenu", "refitToolbar", "addButtons", "shownToolbar", "toolbarGroup", "warnedHere", "sortables", "instanceId", "destroyed", "detailsFor", "moves", "resizes", "sectionNodes", "editableLabels", "lifetime", "addClass", "warnOnceHere", "t", "setLocale", "code", "settingsCopy", "removeConfirmModal", "removeSettingsPanels", "removeDialog", "removeMainControls", "createMainControls", "reset", "operationDepth", "deferredWork", "payloadFor", "kind", "extra", "getView", "emit", "payload", "names", "generic", "canceled", "eventName", "event", "callback", "operate", "body", "defer", "work", "addNode", "insert", "addEventName", "init", "askToDelete", "whenConfirmed", "confirmWith", "confirmed", "answer", "Modal", "modal", "confirmModal", "ok", "one", "pendingAnswer", "settle", "toggleClass", "confirmHandlers", "create", "trackModal", "asking", "retireModal", "panel", "gone", "finish", "modalMoving", "hasClass", "on", "deleteNode", "animate", "planSize", "col", "wanted", "clamp", "getEffectiveOffset", "getSize", "refused", "each", "base", "writes", "cleared", "own", "writeSize", "plan", "write", "setSize", "stripPixelWidths", "withCleared", "resizeColumn", "source", "from", "currentSize", "refreshUtilities", "indentColumn", "offset", "everywhere", "currentOffset", "others", "getOffset", "setOffset", "was", "getEffectiveSize", "positionOf", "parent", "children", "child", "kindOf", "fromPlugin", "FEATURES", "feature", "paneKind", "CONTAINERS", "type", "definition", "sourceHtml", "probe", "setHtml", "newRow", "setup", "watchDrawers", "signal", "onScroll", "delegate", "onContentClick", "e", "pressed", "region", "closest", "targetSelector", "changeTarget", "openSettingsState", "dialogState", "focus", "is", "textReady", "block", "plugins", "refreshPreviews", "overflowMenu", "start", "layout", "grouped", "btn", "rowColsText", "addToTarget", "row", "rowFromLayoutValue", "added", "sizes", "rowColsIcon", "icon", "button", "labelButton", "attr", "createRow", "column", "createColumn", "container", "toolbarGroupOf", "endItems", "toolbarOf", "item", "index", "featureButton", "changeView", "btnGroup", "htmlButton", "closeSource", "openSource", "previewButton", "endPreview", "removeClass", "end", "createGroupTabs", "createOverflowMenu", "makeToolbarDraggable", "CORE_GROUPS", "group", "entry", "tabs", "stash", "tab", "groupLabel", "showGroup", "chosen", "first", "shownAddButtons", "items", "refreshToolbar", "previewing", "more", "toggle", "spares", "spareOf", "home", "menuLifetime", "openOverflow", "fit", "pending", "observer", "open", "homes", "into", "label", "iconClass", "colour", "made", "placed", "inRowOfItsOwn", "toolbarDrags", "buttons", "startToolbarDrag", "startX", "startY", "helper", "far", "move", "onMove", "css", "showDropMarker", "onUp", "up", "off", "hideDropMarker", "swallow", "click", "where", "dropPlaceAt", "insertFromToolbar", "pageX", "pageY", "x", "y", "under", "pluginHooks", "before", "blockSelector", "box", "insertFeatureFromToolbar", "acceptsBlock", "ancestors", "parentsUntil", "top", "rowFromLayout", "widthFamily", "values", "units", "parseSize", "winner", "rowColsWinner", "rowColsLabel", "counts", "widest", "scrollTop", "contentHeight", "outerWidth", "closeSizePicker", "visible", "offers", "textOffers", "convertPlain", "openConvertPicker", "offer", "textBlock", "drawer", "openPicker", "anchor", "choices", "className", "hover", "choice", "withdrawOnLeave", "textTypes", "owners", "entries", "hasTextOwner", "deinit", "show", "hide", "isTarget", "attached", "closeSettings", "closeDialog", "runFilter", "addAllColClasses", "cutter", "textCutter", "splitTexts", "wrapContent", "wrapTexts", "createRowControls", "createColControls", "markContainers", "makeSortable", "makeResizable", "switchLayout", "removeDrawers", "pluginFields", "unwrapTexts", "clearPreviews", "clearRowCols", "unmarkContainers", "removeSortable", "removeResizable", "pluginsWithoutCleanMarkup", "UTILITIES", "registry", "plugin", "marks", "copyCanvas", "copy", "toLive", "toCopy", "live", "copied", "b", "snapshotHtml", "getHtml", "missing", "dropEmptyClass", "marker", "unmarkContainerClasses", "sortableInstance", "list", "removeResizeFurniture", "nodeHtml", "getPlainHtml", "destroy", "loadPlugins", "api", "pluginApi", "registerFamily", "rowColsFamily", "featureWanted", "factory", "family", "methods", "method", "featureMethods", "hook", "argument", "containerId", "defaultRegion", "createTool", "createMoveTool", "addSettingsTool", "place", "createPaneControls", "makeLabelEditable", "labelIn", "unwrapLabels", "suspendToggles", "resumeToggles", "getUtility", "setUtility", "utilityField", "bareStyle", "hostStyle", "setHostStyle", "openDialog", "attachPicker", "detailsOf", "drawerOf", "FAMILIES", "UTILITY_NODES", "PREVIEW_ATTR", "utilitiesOpen", "pluginName", "utility", "familyNamed", "appliesTo", "familiesFor", "utilityClass", "ownUtility", "inheritedUtility", "effectiveUtility", "inherited", "utilityTiers", "writeUtility", "candidate", "readUtility", "planUtility", "viewKey", "property", "original", "details", "hostClasses", "section", "renderUtilities", "renderPluginFields", "utilityNodes", "scope", "selfAndAll", "previewTier", "markRowCols", "styles", "rowColsPreview", "applyPreview", "style", "error", "dropEmptyStyle", "hostDeclaration", "scratch", "declaration", "priority", "check", "previewed", "createUtilitiesSection", "fields", "createField", "settingsScope", "field", "select", "renderField", "fieldNode", "blank", "note", "varies", "labelOf", "custom", "noteNode", "containerCounter", "containerTypeOf", "createContainerControls", "prependDrawer", "hostTools", "tools", "hostTool", "removed", "slideUp", "pane", "confirmText", "remove", "TOGGLE_ATTRIBUTES", "addColumnTo", "attachSizePicker", "tool", "openSizePicker", "timer", "cancel", "room", "spare", "leadingTier", "sizeTitle", "rowColsSource", "smallest", "stepThrough", "currentUnits", "widestFor", "deepestFor", "shrinkAway", "rowContentWidth", "direction", "best", "a", "largest", "FITTED_DRAWERS", "due", "frame", "schedule", "flush", "drawers", "drawerResizes", "fitDrawer", "mutations", "records", "record", "expanded", "drawerOverflows", "limit", "rects", "title", "eventHandlers", "isEditorClass", "setHostClasses", "presets", "createDetails", "toggleSettings", "cssClasses", "detailsDiv", "sectionTitle", "general", "holder", "id", "classGroup", "rowClass", "pluginSections", "utilities", "text", "mode", "panelMode", "sections", "kindLabel", "PANEL_MODES", "settingsPanels", "modalState", "gear", "same", "openSettings", "settingsPanel", "listening", "narrow", "placePopover", "showModal", "hideModal", "closeButton", "removeBackdrop", "gap", "width", "height", "outerHeight", "roomBelow", "roomAbove", "below", "left", "dismissed", "state", "dialogPanel", "dialog", "opener", "paneLabel", "sizedTiers", "hasRowCols", "v", "columnSource", "rowColsUnits", "readUnits", "readEffective", "read", "prefix", "match", "writeUnits", "flex", "ignore", "used", "sibling", "request", "groupName", "accepted", "dragCancelSelector", "sortable", "lists", "Sortable", "wholeDrawer", "soloGroup", "to", "dragged", "sortStart", "sortEnd", "regions", "subject", "moveSubject", "moving", "putBack", "siblings", "resizeEdges", "edge", "handle", "startResizeDrag", "west", "startWidth", "resizeStart", "widthAt", "delta", "resizeMove", "resizeStop", "readout", "snapUnits", "pixels", "next", "balanceSibling", "nextSize", "resize", "nextAll", "resizeReadout", "sizeLabel", "allowed", "balanceAfterResize", "placement", "add", "insertAfter", "apiCreateRow", "apiCreateColumn", "contentFor", "apiCreateContainer", "addPaneTo", "apiAddPane", "isInit", "filters", "func", "cuts", "cut", "area", "pieces", "run", "last", "piece", "hasContent", "createDefaultContentWrapper", "nodes", "contents", "doWrap", "contentArea", "wrap", "createOrphanControls", "createPlainControls", "content", "featureMethod", "file", "apiSetActiveTarget", "named", "result", "GridEditor"]
|
|
4
|
+
"sourcesContent": ["/**\n * The DOM, the way grid-editor uses it.\n *\n * Small helpers over the browser's own API, for the core and the shipped\n * plugins. Not a public API: a plugin of a host's own is free to write its\n * DOM code however it likes, and this file makes no promise to it.\n *\n * Stateless on purpose. The build puts a copy of this file in each plugin's\n * classic script, so anything kept here would be kept once per copy; a\n * module that needs to remember something about a node keeps its own\n * WeakMap.\n */\n\n/** Every element under `root` matching `selector`, as an array. */\nexport function all(root, selector) {\n return root ? Array.prototype.slice.call(root.querySelectorAll(selector)) : [];\n}\n\n/** The first element under `root` matching `selector`, or null. */\nexport function one(root, selector) {\n return root ? root.querySelector(selector) : null;\n}\n\n/** `root` itself when it matches, then every element under it that does. */\nexport function selfAndAll(root, selector) {\n if (!root) { return []; }\n\n var found = all(root, selector);\n if (root.nodeType === 1 && root.matches(selector)) { found.unshift(root); }\n return found;\n}\n\n/** The element children of `node`, those matching `selector` if one is given. */\nexport function children(node, selector) {\n if (!node) { return []; }\n\n return Array.prototype.filter.call(node.children, function(each) {\n return !selector || each.matches(selector);\n });\n}\n\n/** The first element child matching `selector`, or null. */\nexport function child(node, selector) {\n return children(node, selector)[0] || null;\n}\n\n/** The nearest ancestor-or-self matching `selector` below `stopAt`, or null. */\nexport function closest(node, selector, stopAt) {\n var found = node && node.nodeType === 1 ? node.closest(selector) : null;\n\n if (found && stopAt && found !== stopAt && !stopAt.contains(found)) { return null; }\n return found;\n}\n\n/** Whether `node` is an element matching `selector`. */\nexport function is(node, selector) {\n return !!node && node.nodeType === 1 && node.matches(selector);\n}\n\n/** Whether `node` is in the document. */\nexport function attached(node) {\n return !!node && document.documentElement.contains(node);\n}\n\n/** The element siblings after `node` that match `selector`. */\nexport function nextAll(node, selector) {\n var found = [];\n\n for (var next = node.nextElementSibling; next; next = next.nextElementSibling) {\n if (!selector || next.matches(selector)) { found.push(next); }\n }\n return found;\n}\n\n/** The ancestors of `node` up to, and not including, `stop`, nearest first. */\nexport function parentsUntil(node, stop) {\n var found = [];\n\n for (var parent = node.parentElement; parent && parent !== stop; parent = parent.parentElement) {\n found.push(parent);\n }\n return found;\n}\n\n/**\n * The nodes the html parses into, detached. Parsed the way innerHTML parses,\n * so a <script> in it never runs, here or once it is in the page.\n */\nexport function parse(html) {\n var template = document.createElement('template');\n template.innerHTML = html;\n return Array.prototype.slice.call(template.content.childNodes);\n}\n\n/** The one element the html is, detached. */\nexport function create(html) {\n var nodes = parse(html.trim());\n\n for (var i = 0; i < nodes.length; i++) {\n if (nodes[i].nodeType === 1) { return nodes[i]; }\n }\n return null;\n}\n\n/** An element of `tag`, with `attributes` and `text`. */\nexport function element(tag, attributes, text) {\n var node = document.createElement(tag);\n\n Object.keys(attributes || {}).forEach(function(name) {\n var value = attributes[name];\n if (value !== null && value !== undefined && value !== false) { node.setAttribute(name, value); }\n });\n if (text !== undefined && text !== null) { node.textContent = text; }\n\n return node;\n}\n\n/** Replace what `node` holds with `html`. A <script> in it does not run. */\nexport function setHtml(node, html) {\n node.innerHTML = html === undefined || html === null ? '' : String(html);\n return node;\n}\n\n/** Add one or several space separated classes. */\nexport function addClass(node, names) {\n split(names).forEach(function(name) { node.classList.add(name); });\n return node;\n}\n\nexport function removeClass(node, names) {\n split(names).forEach(function(name) { node.classList.remove(name); });\n return node;\n}\n\n/** Each class on, or off, or flipped when `on` is not given. */\nexport function toggleClass(node, names, state) {\n split(names).forEach(function(name) {\n if (state === undefined) {\n node.classList.toggle(name);\n } else {\n node.classList.toggle(name, !!state);\n }\n });\n return node;\n}\n\nexport function hasClass(node, name) {\n return !!node && node.nodeType === 1 && node.classList.contains(name);\n}\n\nfunction split(names) {\n return String(names || '').split(/\\s+/).filter(Boolean);\n}\n\n/** Take the class attribute off when there is nothing left in it. */\nexport function dropEmptyClass(node) {\n if (!node.getAttribute('class')) { node.removeAttribute('class'); }\n return node;\n}\n\n/** Take the style attribute off when there is nothing left in it. */\nexport function dropEmptyStyle(node) {\n if (!node.getAttribute('style')) { node.removeAttribute('style'); }\n return node;\n}\n\n/** Set attributes; a null or undefined value takes the attribute off. */\nexport function attr(node, attributes) {\n Object.keys(attributes).forEach(function(name) {\n var value = attributes[name];\n\n if (value === null || value === undefined) {\n node.removeAttribute(name);\n } else {\n node.setAttribute(name, value);\n }\n });\n return node;\n}\n\n/**\n * Inline styles, by css property name. A number is pixels for the properties\n * that take a length, as jQuery had it; an empty string takes one off.\n */\nexport function css(node, styles) {\n Object.keys(styles).forEach(function(property) {\n var value = styles[property];\n\n if (typeof value === 'number' && !UNITLESS[property]) { value = value + 'px'; }\n node.style.setProperty(property, value === null || value === undefined ? '' : String(value));\n });\n return node;\n}\n\nvar UNITLESS = { opacity: true, 'z-index': true, 'flex-grow': true, 'flex-shrink': true, order: true };\n\n/** What an element of this tag shows as when nothing hides it. */\nvar defaultDisplays = {};\n\nfunction defaultDisplay(node) {\n var tag = node.nodeName;\n\n if (!defaultDisplays[tag]) {\n var probe = document.body.appendChild(document.createElement(tag));\n defaultDisplays[tag] = getComputedStyle(probe).display;\n probe.remove();\n if (defaultDisplays[tag] === 'none') { defaultDisplays[tag] = 'block'; }\n }\n return defaultDisplays[tag];\n}\n\n/** Show a node: its inline display:none off, and a display of its own if a stylesheet hides it. */\nexport function show(node) {\n node.style.removeProperty('display');\n if (getComputedStyle(node).display === 'none') { node.style.display = defaultDisplay(node); }\n return node;\n}\n\nexport function hide(node) {\n node.style.display = 'none';\n return node;\n}\n\n/** Show or hide; flip when `on` is not given. */\nexport function toggle(node, state) {\n if (state === undefined) { state = !visible(node); }\n return state ? show(node) : hide(node);\n}\n\n/** Whether a node takes up room: what jQuery's :visible meant. */\nexport function visible(node) {\n return !!(node.offsetWidth || node.offsetHeight || node.getClientRects().length);\n}\n\n/** The border box's width, fractions included. */\nexport function outerWidth(node) {\n return node.getBoundingClientRect().width;\n}\n\nexport function outerHeight(node) {\n return node.getBoundingClientRect().height;\n}\n\n/** The content box's height, which is what jQuery's height() gave. */\nexport function contentHeight(node) {\n var style = getComputedStyle(node);\n return node.clientHeight - parseFloat(style.paddingTop) - parseFloat(style.paddingBottom);\n}\n\n/** Where a node is on the page, not in the window. */\nexport function offset(node) {\n var box = node.getBoundingClientRect();\n return { top: box.top + window.pageYOffset, left: box.left + window.pageXOffset };\n}\n\n/** Its index among its parent's element children, those matching `selector` if given. */\nexport function indexIn(node, selector) {\n return children(node.parentElement, selector).indexOf(node);\n}\n\n/** Put `node` right after `reference`. */\nexport function insertAfter(node, reference) {\n reference.parentNode.insertBefore(node, reference.nextSibling);\n return node;\n}\n\n/** Replace `node` with what it holds. */\nexport function unwrap(node) {\n var parent = node.parentNode;\n\n while (node.firstChild) { parent.insertBefore(node.firstChild, node); }\n node.remove();\n}\n\n/** Put `node` inside `wrapper`, where `node` was. */\nexport function wrap(node, wrapper) {\n node.parentNode.insertBefore(wrapper, node);\n wrapper.appendChild(node);\n return wrapper;\n}\n\n/**\n * Listen on `root` for `types` (space separated) on descendants that match\n * `selector`, with `this` the matched element, as jQuery's delegated\n * handlers had it. Hands back the listener, for removeEventListener; a\n * signal in `options` removes it too.\n */\nexport function delegate(root, types, selector, handler, options) {\n var listener = function(event) {\n var match = closest(event.target, selector, root);\n if (match && root.contains(match)) { return handler.call(match, event); }\n return undefined;\n };\n\n split(types).forEach(function(type) { root.addEventListener(type, listener, options); });\n return listener;\n}\n\n/** Listen for several space separated event types with one handler. */\nexport function on(target, types, handler, options) {\n split(types).forEach(function(type) { target.addEventListener(type, handler, options); });\n return handler;\n}\n\nexport function off(target, types, handler, options) {\n split(types).forEach(function(type) { target.removeEventListener(type, handler, options); });\n}\n\n/** A mouse event of `type` sent to `node`, the way a pointer would. */\nexport function fire(node, type) {\n node.dispatchEvent(new MouseEvent(type, { bubbles: type !== 'mouseenter' && type !== 'mouseleave' }));\n}\n\n/* ------------------------------------------------------------------\n * Taking a node away, visibly.\n *\n * The durations are jQuery's: 400 ms unless the caller says otherwise. `done` runs once the node is out of sight, which is\n * when the caller removes it; a node that is already out of sight is done at\n * once, on the next task, as jQuery had it.\n * ------------------------------------------------------------------ */\n\nvar DEFAULT_DURATION = 400;\n\nfunction animateAway(node, frames, duration, done) {\n duration = duration === undefined ? DEFAULT_DURATION : duration;\n\n var finish = function() {\n hide(node);\n if (done) { done(); }\n };\n\n if (!visible(node) || !node.animate || duration <= 0) {\n window.setTimeout(finish, 0);\n return;\n }\n\n var animation = node.animate(frames(getComputedStyle(node)), {\n duration: duration,\n easing: 'ease-in-out',\n });\n var called = false;\n var once = function() {\n if (called) { return; }\n called = true;\n finish();\n };\n\n animation.onfinish = once;\n animation.oncancel = once;\n}\n\n/** Fold a node up to nothing, then hide it. */\nexport function slideUp(node, duration, done) {\n if (typeof duration === 'function') {\n done = duration;\n duration = undefined;\n }\n\n node.style.overflow = 'hidden';\n animateAway(node, function(style) {\n return [\n {\n height: style.height,\n paddingTop: style.paddingTop,\n paddingBottom: style.paddingBottom,\n marginTop: style.marginTop,\n marginBottom: style.marginBottom,\n },\n { height: '0px', paddingTop: '0px', paddingBottom: '0px', marginTop: '0px', marginBottom: '0px' },\n ];\n }, duration, function() {\n node.style.removeProperty('overflow');\n if (done) { done(); }\n });\n}\n\n/** Fade a node out, then hide it. */\nexport function fadeOut(node, duration, done) {\n animateAway(node, function(style) {\n return [{ opacity: style.opacity }, { opacity: 0 }];\n }, duration, done);\n}\n\n/** Fade and fold a node, in height and, with `width`, sideways too, then hide it. */\nexport function shrinkAway(node, duration, done, width) {\n node.style.overflow = 'hidden';\n animateAway(node, function(style) {\n var from = { opacity: style.opacity, height: style.height };\n var to = { opacity: 0, height: '0px' };\n\n if (width) {\n from.width = style.width;\n to.width = '0px';\n }\n return [from, to];\n }, duration, function() {\n node.style.removeProperty('overflow');\n if (done) { done(); }\n });\n}\n", "/**\n * Grid editor.\n *\n * A fork of https://github.com/Friendly-Pixel/grid-editor by Simon Epskamp,\n * maintained at https://github.com/themarioga/grid-editor.\n *\n * Plain DOM: nothing here needs jQuery. A page written against the jQuery\n * API loads grideditor.jquery.js beside this file.\n */\nimport * as dom from './dom.js';\n\n/**\n * The methods an instance has, and which of them hand back something other\n * than the instance: html, a view key, a created node. After destroy() every\n * one of them is a no-op that says so once, and the value methods answer\n * null - but for getHtml and getPlainHtml, which read the element as it is.\n */\nvar METHODS = {\n getHtml: { value: true },\n getPlainHtml: { value: true },\n init: {},\n deinit: {},\n reset: {},\n destroy: {},\n changeView: {},\n getView: { value: true },\n createRow: { value: true },\n createColumn: { value: true },\n createElement: { value: true },\n createText: { value: true },\n createSection: { value: true },\n createContainer: { value: true },\n addTab: { value: true },\n addAccordionItem: { value: true },\n addPane: { value: true },\n setLocale: {},\n getUtility: { value: true },\n setUtility: { value: true },\n getActiveTarget: { value: true },\n setActiveTarget: {},\n getSelected: { value: true },\n setSelected: {},\n};\n\n/**\n * Where a create* call may put the node it just made. The first one given\n * wins, and giving none leaves the node detached for the host to place.\n */\nvar PLACEMENTS = ['appendTo', 'prependTo', 'insertAfter', 'insertBefore'];\n\n/**\n * Bootstrap 5's breakpoints, smallest first, which is the order the cascade\n * runs in: a size written for a tier applies to every wider tier that does not\n * override it. Every size and offset class grid-editor reads or writes comes\n * from this table, so adding a tier is a row here and nothing else.\n *\n * `infix` is what Bootstrap's utility classes put between the property and\n * the value - `order-md-2`, `d-none` - and is empty for the smallest tier.\n */\nvar BREAKPOINTS = [\n { key: 'xs', infix: '', colPrefix: 'col-', offsetPrefix: 'offset-', min: 0, preview: 400, labelKey: 'view.xs' },\n { key: 'sm', infix: 'sm', colPrefix: 'col-sm-', offsetPrefix: 'offset-sm-', min: 576, preview: 576, labelKey: 'view.sm' },\n { key: 'md', infix: 'md', colPrefix: 'col-md-', offsetPrefix: 'offset-md-', min: 768, preview: 768, labelKey: 'view.md' },\n { key: 'lg', infix: 'lg', colPrefix: 'col-lg-', offsetPrefix: 'offset-lg-', min: 992, preview: 992, labelKey: 'view.lg' },\n { key: 'xl', infix: 'xl', colPrefix: 'col-xl-', offsetPrefix: 'offset-xl-', min: 1200, preview: 1200, labelKey: 'view.xl' },\n { key: 'xxl', infix: 'xxl', colPrefix: 'col-xxl-', offsetPrefix: 'offset-xxl-', min: 1400, preview: null, labelKey: 'view.xxl' },\n];\n\n/**\n * The view that edits every tier at once. It is the default, and the one most\n * pages want: a layout that needs no per-device tuning is written once, as the\n * class with no breakpoint, and applies at every size.\n */\nvar ALL_VIEW = 'all';\nvar ALL_VIEW_LABEL_KEY = 'view.all';\n\n/** Every view key the dropdown can offer, in the order it offers them. */\nvar VIEW_KEYS = [ALL_VIEW].concat(BREAKPOINTS.map(function(tier) { return tier.key; }));\n\n\nvar MAX_COL_SIZE = 12;\nvar MAX_COL_OFFSET = 11;\n\n/**\n * The two sizes that are not a number of units: `equal` is Bootstrap's col,\n * which shares what the row has left with the other equal columns, and\n * `auto` is col-auto, as wide as its content.\n */\nvar FLEX_SIZES = ['equal', 'auto'];\n\n/** How many columns a row-cols class puts on a line. */\nvar ROW_COLS_VALUES = ['1', '2', '3', '4', '5', '6', 'auto'];\n\nfunction rowColsClass(tier, value) {\n return 'row-cols' + (tier.infix ? '-' + tier.infix : '') + '-' + value;\n}\n\nfunction isUnits(size) {\n return typeof size === 'number';\n}\n\n/** The class that gives a column `size` at one tier: col-md-4, col-md, col-md-auto. */\nfunction sizeClass(tier, size) {\n if (size === 'equal') { return tier.infix ? 'col-' + tier.infix : 'col'; }\n\n return tier.colPrefix + size;\n}\n\nfunction breakpoint(key) {\n for (var i = 0; i < BREAKPOINTS.length; i++) {\n if (BREAKPOINTS[i].key === key) { return BREAKPOINTS[i]; }\n }\n return null;\n}\n\n/**\n * The tier a view writes to. The all view writes the base class, the one\n * with no breakpoint, and takes the others off.\n */\nfunction tiersFor(view) {\n if (view === ALL_VIEW) { return [BREAKPOINTS[0]]; }\n\n var tier = breakpoint(view);\n return tier ? [tier] : [];\n}\n\nfunction labelKeyFor(view) {\n var tier = breakpoint(view);\n return tier ? tier.labelKey : ALL_VIEW_LABEL_KEY;\n}\n\n/**\n * Settings that are objects of grid-editor's own keys rather than something\n * the host owns outright. A host naming one of their keys means \"this one is\n * different\", not \"forget the others\", so these are filled in from their\n * defaults instead of being replaced wholesale.\n */\nvar NESTED_SETTINGS = {\n add_column: {\n size: 12, // What a click on the add column tool adds\n picker: true, // Holding it offers the sizes instead\n delay: 600, // How long to hold, in milliseconds\n },\n elements: {\n enabled: 'auto', // 'auto' turns them on when the page has any\n selector: '[data-ge-element]', // What the host marks an element with\n auto: false, // Treat every child of a content area as an element\n types: [], // The elements the toolbar offers: { type, html, label | labelKey, iconClass, group }\n },\n resize: {\n enabled: true, // The handle on the column's edge\n tools: true, // The narrower and wider tools in the column's drawer\n handles: 'e', // Which edges carry a handle: 'e', 'w', or 'e, w'\n balance: 'next', // 'next' takes the units out of the following column\n },\n indent: {\n tools: true, // The indent tools in the column's drawer\n },\n sidebar: {\n empty: null, // function(ge) -> { title, body } shown while nothing is selected, or null for the message\n },\n drag: {\n delay: 0, // Milliseconds to hold before a drag starts\n touch_delay: 100, // The same for touch, where 0 eats the page's scrolling\n threshold: 3, // Pixels of movement before a gesture counts as a drag\n animation: 150, // Milliseconds of reordering animation, 0 for none\n scroll: true, // Scroll the page when a drag reaches its edge\n },\n};\n\nvar warned = {};\n\n/** Editors on the page, counted so each one's sortable groups are its own. */\nvar editorCounter = 0;\n\n/** The editor on each canvas element, so there is never a second one. */\nvar instances = new WeakMap();\n\n/** The editor whose settings_panel is 'sidebar': a page has one sidebar, so one editor at most. */\nvar sidebarHolder = null;\n\n/** The editor's own controls outside the canvas: a click on one is not a click on the page. */\nvar EDITOR_CONTROLS = '.ge-mainControls, .ge-settings-panel, .ge-sidebar-toggle, .ge-dialog, .ge-confirm, ' +\n '.ge-size-picker, .modal, .modal-backdrop';\n\n/**\n * Translate one key.\n *\n * Lookup order is locale_strings, then the selected locale, then English,\n * then the key itself, so a missing string is a visible key and never an\n * empty tooltip. `params` fills {name} placeholders.\n *\n * Exposed as GridEditor.t for the plugins that have settings and no\n * instance of their own.\n */\nfunction translate(settings, key, params) {\n var locales = GridEditor.locales;\n var locale = locales[settings.locale] || {};\n var overrides = settings.locale_strings || {};\n var string = overrides[key];\n\n if (string === undefined) { string = locale[key]; }\n if (string === undefined) { string = locales.en[key]; }\n\n if (string === undefined) {\n warnOnce('locale:' + key, 'no string for \"' + key + '\" in any locale, showing the key');\n string = key;\n }\n\n return string.replace(/\\{(\\w+)\\}/g, function(placeholder, name) {\n return params && params[name] !== undefined ? params[name] : placeholder;\n });\n}\n\n/** Whether some locale has a string for the key, asked without the warning a missing one gets. */\nfunction hasString(settings, key) {\n var locales = GridEditor.locales;\n\n return (settings.locale_strings || {})[key] !== undefined ||\n (locales[settings.locale] || {})[key] !== undefined ||\n locales.en[key] !== undefined;\n}\n\nfunction warn(message) {\n if (window.console && window.console.warn) {\n window.console.warn('grid-editor: ' + message);\n }\n}\n\n/** Warn about something the host can only usefully be told about once. */\nfunction warnOnce(key, message) {\n if (warned[key]) { return; }\n warned[key] = true;\n warn(message);\n}\n\n/** A string in English, for the few things said before an editor has settings. */\nfunction english(key, params) {\n return translate({ locale: 'en' }, key, params);\n}\n\n/**\n * The element an editor goes on: an element, or the first one a selector\n * matches. Anything else is a mistake worth throwing for, since there is no\n * editor to hand back.\n */\nfunction targetElement(target) {\n if (typeof target === 'string') {\n var found = document.querySelector(target);\n if (!found) { throw new TypeError('grid-editor: no element matches ' + JSON.stringify(target)); }\n return found;\n }\n\n if (target && target.nodeType === 1) { return target; }\n\n throw new TypeError('grid-editor: the target is an element or a selector, not ' +\n (target === null ? 'null' : typeof target));\n}\n\n/** A node a caller handed in, as an element: an element, a selector's first match, or null. */\nfunction nodeFrom(node) {\n if (typeof node === 'string') { return document.querySelector(node); }\n return node && node.nodeType === 1 ? node : null;\n}\n\n/**\n * SortableJS, and Bootstrap's Modal, as the host provided them: assigned to\n * GridEditor by a page that imports them as modules, or the page's globals.\n */\nfunction sortableLibrary() {\n return GridEditor.Sortable || window.Sortable || null;\n}\n\nfunction modalLibrary() {\n var bootstrap = GridEditor.bootstrap || window.bootstrap;\n return bootstrap && bootstrap.Modal ? bootstrap.Modal : null;\n}\n\n/**\n * Html with grid-editor's own marking taken off: the ge-* classes, the\n * column class and the data-ge-* attributes. A div that was only there for\n * the editor - a content area, a bare element or container wrapper - is left\n * with nothing on it, and goes, its children taking its place.\n *\n * The marking is what lets the editor read its markup back, so this is for\n * publishing, not for saving something to edit again.\n */\nfunction plainHtml(html) {\n // Parsed in a document of its own, which is inert: no script in the\n // markup runs and no image starts loading while it is being cleaned\n var root = document.implementation.createHTMLDocument('').body;\n root.innerHTML = html;\n var emptied = [];\n\n dom.all(root, '*').forEach(function(node) {\n var marked = false;\n\n Array.prototype.slice.call(node.attributes).forEach(function(attribute) {\n if (attribute.name.indexOf('data-ge-') === 0) {\n node.removeAttribute(attribute.name);\n marked = true;\n }\n });\n\n var classes = (node.getAttribute('class') || '').split(/\\s+/).filter(Boolean);\n var kept = classes.filter(function(name) {\n return name !== 'column' && name.indexOf('ge-') !== 0;\n });\n if (kept.length !== classes.length) { marked = true; }\n if (kept.length) {\n node.setAttribute('class', kept.join(' '));\n } else {\n node.removeAttribute('class');\n }\n\n if (marked && node.tagName === 'DIV' && !node.attributes.length) {\n emptied.push(node);\n }\n });\n\n emptied.forEach(function(div) {\n dom.unwrap(div);\n });\n\n return root.innerHTML;\n}\n\n/**\n * An editor on `target`: an element, or the first one a selector matches.\n *\n * var ge = new GridEditor('#myGrid', { new_row_layouts: [[12], [6, 6]] });\n * var html = ge.getHtml();\n *\n * An element carries one editor at most: asked for a second, this hands back\n * the one it has, with the options it was made with, and says so once.\n */\nfunction GridEditor(target, options) {\n var element = targetElement(target);\n var existing = instances.get(element);\n\n if (existing) {\n if (!doubleWarned.has(element)) {\n doubleWarned.add(element);\n warn(english('warning.already_editing'));\n }\n return existing;\n }\n\n if (!(this instanceof GridEditor)) { return new GridEditor(element, options); }\n\n build(this, element, options || {});\n}\n\n/** The elements a second editor was asked for on, so each is told about once. */\nvar doubleWarned = new WeakSet();\n\nGridEditor.create = function(target, options) {\n return new GridEditor(target, options);\n};\n\n/** The editor on `target`, or null. */\nGridEditor.get = function(target) {\n var element = nodeFrom(target);\n return element ? instances.get(element) || null : null;\n};\n\nfunction build(instance, baseElem, optionsOrMethod) {\n\n var settings = Object.assign({\n 'new_row_layouts' : [ // Column layouts for add row buttons\n [12],\n [6, 6],\n [4, 4, 4],\n [3, 3, 3, 3],\n [2, 2, 2, 2, 2, 2],\n [2, 8, 2],\n [4, 8],\n [8, 4]\n ],\n 'row_classes' : [], // Preset class toggles, on top of the classes field\n 'col_classes' : [],\n 'col_tools' : [], /* Example:\n [ {\n title: 'Set background image',\n iconClass: 'bi bi-image',\n on: { click: function(event) {} }\n } ]\n */\n 'row_tools' : [],\n 'drag_handle' : 'tool', // 'tool' for the move tool, 'drawer' for the whole drawer\n 'toolbar_drag' : 'auto', // Drag the toolbar's buttons onto the canvas. 'auto' follows drag_handle\n 'toolbar_overflow' : 'menu', // What doesn't fit on one line: 'menu' behind a button, 'wrap' onto another line\n 'drawer_overflow' : 'menu', // The same for the drawers' tools: 'menu' behind a button, 'wrap' onto another line\n 'toolbar_groups' : false, // The add buttons in categories, one shown at a time, picked with tabs\n 'active_target' : false, // A click in a column makes it where the toolbar's buttons add\n 'element_tools' : [], // Host tools on element drawers, same shape as row_tools\n 'element_classes' : [], // Preset class toggles on an element's settings panel\n // content_types, text_tools and text_classes are the text editor\n // plugins' settings: see grideditor.text.js\n 'container_classes' : [], // The same, on a container's panel\n 'pane_classes' : [], // And on a tab's or an accordion item's\n 'container_tools' : [], // Host tools on container drawers\n 'tab_tools' : [], // Host tools on tab drawers\n 'accordion_tools' : [], // Host tools on accordion item drawers\n 'plugins' : null, // Plugins to use, of any kind; null means every one loaded\n 'row_cols' : true, // A row's \"columns per row\" field, row-cols-*\n 'utilities' : {}, // Options for the utility plugins, by plugin name\n 'elements' : NESTED_SETTINGS.elements, // Element level controls, below the column\n 'custom_filter' : '',\n 'valid_col_sizes' : [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 'equal', 'auto'],\n 'valid_col_offsets' : [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11],\n 'add_column' : NESTED_SETTINGS.add_column, // The add column tool\n 'layout_modes' : VIEW_KEYS.slice(), // Which views the dropdown offers\n 'default_view' : ALL_VIEW,\n 'resize' : NESTED_SETTINGS.resize, // Resizing a column by dragging its edge\n 'indent' : NESTED_SETTINGS.indent, // Indenting a column, offset-*\n 'source_textarea' : '',\n 'edit_source' : true, // The toolbar's button to edit the canvas as html\n 'locale' : 'en', // Code of a locale in GridEditor.locales\n 'locale_strings' : {}, // Overrides for individual keys\n 'callbacks' : {}, // before_*/after_* functions, the events by another route\n 'confirm_delete' : true, // Ask before deleting a row or a column\n 'settings_panel' : 'offcanvas', // Where a node's settings open: 'offcanvas', 'popover', 'modal', 'inline' or 'sidebar'\n 'sidebar' : NESTED_SETTINGS.sidebar, // The 'sidebar' panel: what it shows while nothing is selected\n 'drag' : NESTED_SETTINGS.drag // How a drag behaves, whatever drives it\n }, optionsOrMethod);\n\n // Merged rather than replaced, so `elements: { auto: true }` keeps the\n // default selector instead of losing it\n Object.keys(NESTED_SETTINGS).forEach(function(name) {\n settings[name] = Object.assign({}, NESTED_SETTINGS[name], settings[name]);\n });\n\n\n // Elems\n var canvas,\n mainControls,\n wrapper, // controls wrapper\n addRowGroup,\n addContainerGroup,\n layoutDropdown,\n htmlTextArea\n ;\n var curView = settings.default_view; // Breakpoint key, or 'all'\n var confirmDialog = null; // The delete confirmation, built when first needed\n var sizePicker = null; // The open column size picker, if there is one\n var sourceOpen = false; // Whether the canvas is being edited as html\n var dropMarker = null; // The line showing where a dragged toolbar button would land\n var activeTarget = null; // The column or region the toolbar adds to, with active_target\n var toolbarLifetime = null; // Aborted when the toolbar is rebuilt or taken away\n var closeOverflowMenu = function() {}; // Folds the toolbar's overflow menu away, when it has one\n var refitToolbar = function() {}; // Works out again what the toolbar's overflow menu holds, when it has one\n var addButtons = []; // The toolbar's add buttons, in toolbar order: { button, home, group }\n var shownToolbar = {}; // Each feature plugin's toolbar items, as the toolbar was last built with them\n var toolbarGroup = null; // The category shown, with toolbar_groups. Kept when the toolbar is rebuilt\n var warnedHere = {}; // Some warnings are worth saying once per instance, not once per call\n var sortables = []; // Every list made sortable, so deinit destroys exactly those\n var instanceId = ++editorCounter; // Scopes the sortable groups to this editor\n var destroyed = false;\n var selected = null; // The node whose settings the sidebar shows, with settings_panel 'sidebar'\n var sidebarCollapsed = null; // Folded away, once the sidebar has been shown: the window's width decides the first time\n var pluginHandle = null; // What the plugins were handed, for the hooks that call them back\n\n if (settings.settings_panel === 'sidebar') {\n if (sidebarHolder) {\n warnOnceHere('sidebar', 'settings_panel \"sidebar\" is in use by another editor on the page, which has one ' +\n 'sidebar: using offcanvas');\n settings.settings_panel = 'offcanvas';\n } else {\n sidebarHolder = instance;\n }\n }\n\n // What the editor remembers about the nodes it edits, which used to\n // be jQuery data: a node's settings panel, a drag or a resize in\n // progress. Kept off the markup, and gone with the node.\n var detailsFor = new WeakMap(); // node -> its settings panel\n var moves = new WeakMap(); // dragged node -> { from, canceled }\n var resizes = new WeakMap(); // column -> { from, units }\n var sectionNodes = new WeakMap(); // Responsive section -> the node it edits\n var editableLabels = new WeakSet(); // labels made editable in place\n\n // Listeners the editor puts on things it does not own - the window,\n // the document, the canvas - taken off together by destroy()\n var lifetime = new AbortController();\n\n // Before anything else, because the instance hands the canvas to\n // hosts and the rest of setup() runs at the end of this function\n canvas = dom.addClass(baseElem, 'ge-canvas');\n\n function warnOnceHere(key, message) {\n if (warnedHere[key]) { return; }\n warnedHere[key] = true;\n warn(message);\n }\n\n /** This instance's strings, in the locale its settings asked for. */\n function t(key, params) {\n return translate(settings, key, params);\n }\n\n /**\n * Swap language at runtime. The controls carry their strings in\n * attributes, so they are rebuilt rather than patched.\n */\n function setLocale(code) {\n settings.locale = code;\n instance.settings = settingsCopy();\n\n removeConfirmModal();\n removeSettingsPanels();\n removeDialog();\n removeMainControls();\n createMainControls();\n reset();\n }\n\n var operationDepth = 0; // Operations running right now\n var deferredWork = []; // What handlers asked for while one was running\n\n /**\n * The payload every notification carries. Built here, and only here,\n * so no caller assembles one by hand and gets a field wrong.\n *\n * `parent` is where the node is going, or where it is coming from on a\n * delete, which is not the same as the node's parent while the node is\n * still detached - so an add passes it in.\n */\n function payloadFor(kind, node, extra) {\n return Object.assign({\n kind: kind,\n node: node,\n parent: node.parentElement,\n canvas: canvas,\n breakpoint: getView(),\n source: 'api',\n }, extra || {});\n }\n\n /**\n * Deliver one notification twice: as a DOM event on the canvas - the\n * specific name first, then the generic one - and as the matching\n * settings.callbacks entries. Everything is delivered whatever the\n * first listener says, and the answer is whether any of them canceled,\n * which only means something for a before-* notification.\n *\n * A listener that throws is the browser's to report: the other\n * listeners, the callbacks and the operation go on.\n */\n function emit(name, payload) {\n var names = [name];\n var generic = name.replace(/^(before|after)-add-.+$/, '$1-add');\n if (generic !== name) { names.push(generic); }\n\n var canceled = false;\n\n names.forEach(function(eventName) {\n var event = new CustomEvent('grideditor:' + eventName, {\n detail: payload,\n bubbles: true,\n cancelable: true,\n });\n if (!canvas.dispatchEvent(event)) { canceled = true; }\n });\n\n names.forEach(function(eventName) {\n var callback = settings.callbacks[eventName.replace(/-/g, '_')];\n if (typeof callback == 'function' && callback(payload) === false) {\n canceled = true;\n }\n });\n\n return !canceled;\n }\n\n /**\n * One operation, from its before-* notification to its after-* one.\n *\n * Anything a handler asks the editor to do while the operation runs is\n * queued and played back once it finishes, so a handler cannot reset\n * the canvas out from under the operation that called it.\n */\n function operate(body) {\n operationDepth++;\n try {\n return body();\n } finally {\n operationDepth--;\n if (operationDepth === 0) {\n while (deferredWork.length) {\n deferredWork.shift()();\n }\n }\n }\n }\n\n /** Run `work` now, or after the running operation if there is one. */\n function defer(work) {\n if (operationDepth === 0) {\n work();\n return;\n }\n\n deferredWork.push(work);\n }\n\n /**\n * Insert a node: ask, insert, bring the canvas up to date so the new\n * markup has its controls, then announce it. Hands back the node, or\n * null when a handler canceled.\n *\n * The update is init() rather than reset(): a reset deinitializes\n * every rich text editor on the canvas, and adding a row somewhere\n * else is no reason to close the editor the user is typing in.\n */\n function addNode(kind, node, insert, extra) {\n var name = addEventName(kind);\n\n return operate(function() {\n var payload = payloadFor(kind, node, extra);\n\n if (!emit('before-add-' + name, payload)) { return null; }\n\n insert();\n init();\n emit('after-add-' + name, payload);\n\n return node;\n });\n }\n\n /**\n * Every container type shares one pair of add events, with the\n * payload's kind saying which type it was: a host that cares about\n * containers binds one name, not three.\n */\n function addEventName(kind) {\n return GridEditor.containers[kind] ? 'container' : kind;\n }\n\n /**\n * Ask the user, in Bootstrap's own modal.\n *\n * Bootstrap is already a dependency of an editor for Bootstrap's grid,\n * and window.confirm cannot be styled, cannot be translated by us and\n * blocks the page while it is up. The modal lives outside the canvas,\n * so it is never part of what getHtml returns.\n *\n * A page that loaded Bootstrap's css but not its javascript still gets\n * asked - by the browser, as before. A page that imports Bootstrap as\n * a module hands its Modal over as GridEditor.bootstrap.\n */\n function askToDelete(message, whenConfirmed) {\n if (!settings.confirm_delete) {\n whenConfirmed();\n return;\n }\n\n confirmWith(message, { danger: true }, function(confirmed) {\n if (confirmed) { whenConfirmed(); }\n });\n }\n\n /**\n * ge.confirm(): a question of a plugin's own, in the same modal.\n * `answer` is called once: true for the ok button, false for cancel,\n * the close button or Escape, and null when the question goes\n * unanswered because the modal is taken away - setLocale, destroy, or\n * another question asked over it.\n */\n function confirmWith(message, options, answer) {\n options = options || {};\n var Modal = modalLibrary();\n\n if (!Modal) {\n answer(window.confirm(message));\n return;\n }\n\n var modal = confirmModal();\n var confirmed = false;\n var ok = dom.one(modal, '.ge-confirm-ok');\n\n // The question before this one, if it is still up, goes unanswered\n if (pendingAnswer) { pendingAnswer(null); }\n\n var settle = function(value) {\n if (pendingAnswer !== settle) { return; }\n pendingAnswer = null;\n answer(value);\n };\n pendingAnswer = settle;\n\n dom.one(modal, '.modal-title').textContent = options.title || t('confirm.title');\n dom.one(modal, '.ge-confirm-cancel').textContent = options.cancel || t('confirm.cancel');\n ok.textContent = options.ok || t('confirm.ok');\n dom.toggleClass(ok, 'btn-danger', !!options.danger);\n dom.toggleClass(ok, 'btn-primary', !options.danger);\n\n dom.one(modal, '.ge-confirm-message').textContent = message;\n ok.onclick = function() {\n confirmed = true;\n Modal.getInstance(modal).hide();\n };\n\n confirmHandlers.hidden = function() {\n // After the modal is out of the way, so the backdrop is not\n // sitting over the animation a delete runs\n settle(confirmed);\n };\n\n confirmHandlers.shown = function() {\n ok.focus();\n };\n\n Modal.getOrCreateInstance(modal).show();\n }\n\n // What the confirm modal does when Bootstrap says it is shown or\n // hidden: this question's answer, replaced by the next question's\n var confirmHandlers = { hidden: null, shown: null };\n var pendingAnswer = null; // The open question's answer, until it is given\n\n /** Built once per instance, and taken away again by destroy(). */\n function confirmModal() {\n if (confirmDialog) { return confirmDialog; }\n\n confirmDialog = dom.create(\n '<div class=\"modal fade ge-confirm\" tabindex=\"-1\" aria-hidden=\"true\">' +\n '<div class=\"modal-dialog modal-dialog-centered\">' +\n '<div class=\"modal-content\">' +\n '<div class=\"modal-header\">' +\n '<h5 class=\"modal-title\"></h5>' +\n '<button type=\"button\" class=\"btn-close\" data-bs-dismiss=\"modal\"></button>' +\n '</div>' +\n '<div class=\"modal-body\"><p class=\"ge-confirm-message\"></p></div>' +\n '<div class=\"modal-footer\">' +\n '<button type=\"button\" class=\"btn btn-secondary ge-confirm-cancel\" data-bs-dismiss=\"modal\"></button>' +\n '<button type=\"button\" class=\"btn btn-danger ge-confirm-ok\"></button>' +\n '</div>' +\n '</div>' +\n '</div>' +\n '</div>'\n );\n document.body.appendChild(confirmDialog);\n\n dom.one(confirmDialog, '.modal-title').textContent = t('confirm.title');\n dom.one(confirmDialog, '.btn-close').setAttribute('aria-label', t('confirm.cancel'));\n dom.one(confirmDialog, '.ge-confirm-cancel').textContent = t('confirm.cancel');\n dom.one(confirmDialog, '.ge-confirm-ok').textContent = t('confirm.ok');\n\n trackModal(confirmDialog);\n // Only while it is the modal asking: one being taken away -\n // setLocale builds another - finishes hiding after the next\n // question is up, and that answer is not its to give\n var asking = confirmDialog;\n confirmDialog.addEventListener('hidden.bs.modal', function() {\n if (asking === confirmDialog && confirmHandlers.hidden) { confirmHandlers.hidden(); }\n });\n confirmDialog.addEventListener('shown.bs.modal', function() {\n if (asking === confirmDialog && confirmHandlers.shown) { confirmHandlers.shown(); }\n });\n\n return confirmDialog;\n }\n\n /** The confirm modal is rebuilt in the new language on setLocale. */\n function removeConfirmModal() {\n if (!confirmDialog) { return; }\n\n // Its answer is not wanted any more: the editor it asked for is going\n confirmHandlers.hidden = null;\n confirmHandlers.shown = null;\n retireModal(confirmDialog);\n confirmDialog = null;\n\n // A plugin's question goes unanswered, and the plugin is told so\n if (pendingAnswer) { pendingAnswer(null); }\n }\n\n /**\n * Take a Bootstrap modal away. One out of sight goes at once. One that\n * is showing, or on its way in or out, is asked to hide and goes when\n * Bootstrap says it is hidden: Bootstrap finishes a transition on the\n * node it started it on, and a node taken away under it throws, and\n * leaves the page's body locked, with no scrolling.\n */\n function retireModal(panel) {\n var Modal = modalLibrary();\n var modal = Modal ? Modal.getInstance(panel) : null;\n var gone = false;\n var finish = function() {\n if (gone) { return; }\n gone = true;\n if (modal) { modal.dispose(); }\n panel.remove();\n };\n\n if (!modal || (!modalMoving.get(panel) && !dom.hasClass(panel, 'show'))) {\n finish();\n return;\n }\n\n panel.addEventListener('hidden.bs.modal', finish, { once: true });\n // Still on its way in, it ignores a hide: once it is in, it takes one\n panel.addEventListener('shown.bs.modal', function() { modal.hide(); }, { once: true });\n modal.hide();\n }\n\n /** Whether a modal is between Bootstrap's show and shown, or hide and hidden. */\n var modalMoving = new WeakMap();\n\n function trackModal(panel) {\n dom.on(panel, 'show.bs.modal hide.bs.modal', function() { modalMoving.set(panel, true); });\n dom.on(panel, 'shown.bs.modal hidden.bs.modal', function() { modalMoving.set(panel, false); });\n }\n\n /**\n * Remove a node: ask the host, then the user, then remove it, update\n * the canvas and announce it once the animation has finished.\n *\n * The host's handler goes first on purpose. A host that cancels\n * before-delete to ask in its own way does not want the built-in\n * question to have been asked already.\n */\n function deleteNode(kind, node, message, animate) {\n operate(function() {\n var payload = payloadFor(kind, node, { source: 'tool' });\n\n if (!emit('before-delete', payload)) { return; }\n\n askToDelete(message, function() {\n operate(function() {\n animate(function() {\n node.remove();\n operate(function() {\n init();\n emit('after-delete', payload);\n });\n });\n });\n });\n });\n }\n\n /**\n * What resizing this column to `size` in `view` would write, or null\n * when the budget refuses it or there is nothing to change.\n *\n * A breakpoint view writes its own tier. The all view writes the base\n * class and takes the size off every other tier, so one size is what\n * applies everywhere; the plan says what it took off.\n *\n * Refused rather than quietly clamped: the offset is something the\n * user set, and a tool that rewrites it is a tool that lies. In the\n * all view the base size has to fit every tier's offset, since it is\n * the size at every tier once the others are gone.\n */\n function planSize(col, size, view) {\n view = view || curView;\n\n if (view !== ALL_VIEW) {\n var tier = breakpoint(view);\n var wanted = clamp({ size: size, offset: getEffectiveOffset(col, tier) || 0 });\n\n if (wanted.refused || getSize(col, tier) === wanted.size) { return null; }\n\n return { writes: [{ tier: tier, size: wanted.size }], cleared: null, size: wanted.size };\n }\n\n var refused = BREAKPOINTS.some(function(each) {\n return clamp({ size: size, offset: getEffectiveOffset(col, each) || 0 }).refused;\n });\n if (refused) { return null; }\n\n var base = BREAKPOINTS[0];\n var writes = [];\n var cleared = [];\n\n BREAKPOINTS.slice(1).forEach(function(each) {\n var own = getSize(col, each);\n if (own === null) { return; }\n\n writes.push({ tier: each, size: null });\n cleared.push({ breakpoint: each.key, value: own });\n });\n\n if (getSize(col, base) !== size) { writes.unshift({ tier: base, size: size }); }\n\n return writes.length ? { writes: writes, cleared: cleared, size: size } : null;\n }\n\n function writeSize(col, plan) {\n plan.writes.forEach(function(write) { setSize(col, write.tier, write.size); });\n stripPixelWidths(col);\n }\n\n /** The all view's payloads say what the write took off the breakpoints. */\n function withCleared(extra, cleared) {\n if (cleared) { extra.cleared = cleared; }\n return extra;\n }\n\n /**\n * Resize a column, announcing it either side. `size` is units,\n * `equal` or `auto`; `view` is the current one unless the size field\n * of a plugin's panel says otherwise.\n */\n function resizeColumn(col, size, source, view) {\n view = view || curView;\n\n var from = currentSize(col);\n var plan = planSize(col, size, view);\n\n if (!plan) { return false; }\n\n return operate(function() {\n var payload = payloadFor('column', col, withCleared({\n source: source,\n breakpoint: view,\n from: from,\n to: plan.size,\n }, plan.cleared));\n\n if (!emit('before-resize', payload)) {\n refreshUtilities(col);\n return false;\n }\n\n writeSize(col, plan);\n refreshUtilities(col);\n emit('after-resize', payload);\n\n return true;\n });\n }\n\n /**\n * Indent a column, shrinking it when the budget needs it: the offset\n * is what the user asked for, so it is the one that gets its way.\n *\n * Like a size, an offset is written to the tier being edited, or in\n * the all view as the base class with every other tier's taken off.\n */\n function indentColumn(col, offset, source) {\n var everywhere = curView === ALL_VIEW;\n var tier = everywhere ? BREAKPOINTS[0] : breakpoint(curView);\n var from = currentOffset(col);\n\n offset = Math.min(Math.max(offset, 0), MAX_COL_OFFSET);\n\n var others = everywhere ? BREAKPOINTS.slice(1).filter(function(each) {\n return getOffset(col, each) !== null;\n }) : [];\n\n if ((getOffset(col, tier) || 0) === offset && !others.length) { return false; }\n\n return operate(function() {\n var payload = payloadFor('column', col, withCleared({\n source: source,\n from: from,\n to: offset,\n }, everywhere ? others.map(function(each) {\n return { breakpoint: each.key, value: getOffset(col, each) };\n }) : null));\n\n if (!emit('before-indent', payload)) { return false; }\n\n setOffset(col, tier, offset);\n others.forEach(function(each) { setOffset(col, each, 0); });\n\n // Wherever the column's size and the new offset no longer fit\n // - one tier, or every tier in the all view - the size gives\n // way, at that tier only. An equal or auto column fits anywhere.\n (everywhere ? BREAKPOINTS : [tier]).forEach(function(each) {\n var was = getEffectiveSize(col, each);\n if (!isUnits(was)) { return; }\n\n var wanted = clamp({ size: was, offset: offset, leading: 'offset' });\n if (wanted.size !== was) { setSize(col, each, wanted.size); }\n });\n\n refreshUtilities(col);\n emit('after-indent', payload);\n\n return true;\n });\n }\n\n /**\n * Where a node sits, for the from/to of a move. Tool drawers are not\n * counted, so the index is the one a host would recognize.\n */\n function positionOf(node) {\n var parent = node.parentElement;\n\n return {\n parent: parent,\n index: dom.children(parent).filter(function(child) {\n return !dom.hasClass(child, 'ge-tools-drawer');\n }).indexOf(node),\n };\n }\n\n function kindOf(node) {\n var fromPlugin = null;\n\n Object.keys(FEATURES).forEach(function(name) {\n var feature = FEATURES[name];\n if (!fromPlugin && feature.kindOf) { fromPlugin = feature.kindOf(node); }\n });\n if (fromPlugin) { return fromPlugin; }\n\n if (node.getAttribute('data-ge-container')) { return node.getAttribute('data-ge-container'); }\n\n // A container plugin's pane, by the class it marks its panes with\n var paneKind = null;\n Object.keys(CONTAINERS).forEach(function(type) {\n var definition = CONTAINERS[type];\n if (!paneKind && definition.paneClass && dom.hasClass(node, definition.paneClass)) {\n paneKind = definition.paneKind;\n }\n });\n if (paneKind) { return paneKind; }\n\n if (dom.hasClass(node, 'ge-tab')) { return 'tab'; }\n if (dom.hasClass(node, 'ge-accordion-item')) { return 'accordion-item'; }\n if (dom.hasClass(node, 'row')) { return 'row'; }\n if (dom.hasClass(node, 'column')) { return 'column'; }\n if (dom.hasClass(node, 'ge-element')) { return 'element'; }\n // A content area is a text when an editor's type is on it, and the\n // host's plain content when there is none\n if (dom.hasClass(node, 'ge-text-block')) { node = dom.child(node, '.ge-content') || node; }\n if (dom.hasClass(node, 'ge-content')) { return node.getAttribute('data-ge-content-type') ? 'text' : 'plain'; }\n return 'node';\n }\n\n // Copy html to sourceElement if a source textarea is given\n if (settings.source_textarea) {\n var sourceHtml = nodeFrom(settings.source_textarea).value;\n // Html with no grid in it goes into a row and a full width column\n // of its own, where init wraps it as the host's plain content\n var probe = dom.element('div');\n probe.innerHTML = sourceHtml;\n if (sourceHtml.length > 0 && !probe.querySelector('.row')) {\n sourceHtml = '<div class=\"row\"><div class=\"col-lg-12\">' + sourceHtml + '</div></div>';\n }\n dom.setHtml(baseElem, sourceHtml);\n }\n\n // Wrap content if it is non-bootstrap\n if (baseElem.children.length && !baseElem.querySelector('div.row')) {\n var children = dom.children(baseElem);\n var newRow = dom.create('<div class=\"row\"><div class=\"col-lg-12\"></div></div>');\n baseElem.appendChild(newRow);\n children.forEach(function(child) { newRow.firstChild.appendChild(child); });\n }\n\n // setup() and init() run at the end of this function, once every\n // table and helper below has been assigned: the toolbar is built from\n // the container registry, and a var declared later is not there yet.\n\n function setup() {\n htmlTextArea = dom.element('textarea', { 'class': 'ge-html-output' });\n canvas.parentNode.insertBefore(htmlTextArea, canvas);\n\n createMainControls();\n watchDrawers();\n\n var signal = { signal: lifetime.signal };\n\n // Make controls fixed on scroll\n window.addEventListener('scroll', onScroll, signal);\n\n /* A click on the host's plain content offers to make it a text */\n dom.delegate(canvas, 'click', '.ge-content', onContentClick, signal);\n\n /* A trigger is often a link, and a link still navigates even\n with its Bootstrap attributes suspended */\n dom.delegate(canvas, 'click', '.ge-popup-trigger, [data-ge-popup-target]', function(e) {\n if (dom.hasClass(canvas, 'ge-editing')) { e.preventDefault(); }\n }, signal);\n\n var sidebarMode = panelMode() === 'sidebar';\n\n if (settings.active_target || sidebarMode) {\n // The click a drag ends in - a resize, a move - is not one:\n // it comes where the pointer let go, not where it pressed\n var pressed = null;\n canvas.addEventListener('pointerdown', function(e) {\n pressed = { x: e.clientX, y: e.clientY };\n }, signal);\n canvas.addEventListener('click', function(e) {\n var from = pressed;\n pressed = null;\n if (!dom.hasClass(canvas, 'ge-editing')) { return; }\n if (from && Math.abs(e.clientX - from.x) + Math.abs(e.clientY - from.y) > settings.drag.threshold) { return; }\n\n if (settings.active_target) { clickTarget(e); }\n // A tool that took its node off the canvas says nothing of where the click was\n if (sidebarMode && canvas.contains(e.target)) { changeSelection(settingsNodeAt(e.target)); }\n }, signal);\n\n // Escape is the panel's, the dialog's, and a field's or a\n // text's while one has the focus; after those, it is the\n // selection's, and then the target's\n document.addEventListener('keydown', function(e) {\n if (e.key !== 'Escape' || openSettingsState || dialogState) { return; }\n if (confirmDialog && dom.hasClass(confirmDialog, 'show')) { return; }\n var focus = document.activeElement;\n if (focus && (dom.is(focus, 'input, textarea, select') || focus.isContentEditable)) { return; }\n\n if (selected && isEditing()) {\n changeSelection(null);\n } else if (activeTarget) {\n changeTarget(null);\n }\n }, signal);\n }\n\n if (sidebarMode) {\n // The focus coming into a node selects it, as a click does\n canvas.addEventListener('focusin', function(e) {\n var node = isEditing() ? settingsNodeAt(e.target) : null;\n if (node) { changeSelection(node); }\n }, signal);\n\n // A click on the page, away from the canvas and the editor's own\n // controls, puts the selection away - not while a text is open,\n // whose editor has controls of its own out there\n document.addEventListener('click', function(e) {\n var target = e.target;\n if (!selected || !isEditing() || !target || target.nodeType !== 1) { return; }\n if (!dom.attached(target) || canvas.contains(target)) { return; }\n if (dom.closest(target, EDITOR_CONTROLS) || canvas.querySelector('.ge-rte-active')) { return; }\n\n changeSelection(null);\n }, signal);\n\n window.addEventListener('resize', reserveSidebarRoom, signal);\n }\n\n /* Whatever the click was for - a text, a tool - it also says\n where the toolbar adds next. A click on no column or region\n says nowhere, and the toolbar adds to the canvas again. */\n function clickTarget(e) {\n var region = dom.closest(e.target, targetSelector());\n\n // The target's own background, or its drawer's, clicked\n // again takes it back. What is in it - a text, a tool, a\n // nested column - keeps it, or makes that the target\n if (region && region === activeTarget &&\n (e.target === region || e.target === dom.child(region, '.ge-tools-drawer'))) {\n changeTarget(null);\n return;\n }\n\n changeTarget(region && region !== canvas && canvas.contains(region) ? region : null);\n }\n }\n\n /**\n * A rich text editor rewrites the content area as it takes over,\n * which costs the element drawers inside it. The integrations say\n * when their editor is ready, and the drawers go back in.\n */\n function textReady(block) {\n if (!dom.is(block, '.ge-content') || !canvas.contains(block)) { return; }\n\n plugins('onContentReady', block);\n refreshPreviews(block);\n }\n\n /**\n * The toolbar above the canvas. Separate from setup() because every\n * string in it comes from the locale, so setLocale() rebuilds it.\n */\n function createMainControls() {\n mainControls = dom.element('div', { 'class': 'ge-mainControls' });\n htmlTextArea.parentNode.insertBefore(mainControls, htmlTextArea);\n wrapper = mainControls.appendChild(dom.element('div', { 'class': 'ge-wrapper ge-top' }));\n\n // With the overflow menu, the add buttons stand in a line of\n // their own that keeps to one line, beside the menu's button\n var overflowMenu = settings.toolbar_overflow !== 'wrap';\n var start = wrapper;\n if (overflowMenu) {\n dom.addClass(wrapper, 'ge-toolbar-menu');\n start = wrapper.appendChild(dom.element('div', { 'class': 'ge-toolbar-start' }));\n }\n\n addButtons = [];\n\n // Add row\n addRowGroup = start.appendChild(dom.element('div', { 'class': 'ge-addRowGroup btn-group' }));\n addContainerGroup = dom.element('div', { 'class': 'ge-addContainerGroup btn-group ms-1' });\n settings.new_row_layouts.forEach(function(layout) {\n var grouped = !Array.isArray(layout);\n var btn = dom.element('a', {\n 'class': 'btn btn-sm btn-light',\n title: grouped\n ? t('row.add_row_cols', { columns: layout.columns, counts: rowColsText(layout.row_cols) })\n : t('row.add', { layout: layout.join('-') }),\n // What this button makes, in the markup rather than in\n // memory: a drag works on a clone of it\n 'data-ge-toolbar': 'row',\n 'data-ge-layout': grouped ? JSON.stringify(layout) : layout.join(','),\n });\n\n btn.addEventListener('click', function() {\n if (activeTarget) { addToTarget(btn, 'tool'); return; }\n\n var row = rowFromLayoutValue(layout);\n\n var added = addNode('row', row, function() {\n canvas.appendChild(row);\n }, { parent: canvas, source: 'tool' });\n\n if (added && row.scrollIntoView) {\n row.scrollIntoView({behavior: 'smooth'});\n }\n });\n addRowGroup.appendChild(btn);\n addButtons.push({ button: btn, home: addRowGroup, group: 'rows' });\n\n btn.appendChild(dom.create('<i class=\"bi bi-plus\"></i>'));\n\n // A row of columns shares out the icon as they share the row;\n // a row with row-cols draws one line of its widest count\n var sizes = grouped ? rowColsIcon(layout) : layout;\n var icon = '<div class=\"row ge-row-icon\">';\n sizes.forEach(function(size) {\n icon += '<div class=\"column ' + sizeClass(BREAKPOINTS[0], size) + '\"></div>';\n });\n icon += '</div>';\n btn.appendChild(dom.create(icon));\n });\n\n start.appendChild(addContainerGroup);\n\n // A container starts in a row of its own, the way the add row\n // buttons next to these ones do\n Object.keys(CONTAINERS).forEach(function(type) {\n var definition = CONTAINERS[type];\n var button = labelButton(dom.element('a', { 'class': 'btn btn-sm btn-light ge-add-container' }),\n t(definition.labelKey), definition.iconClass);\n\n dom.attr(button, { 'data-ge-toolbar': 'container', 'data-ge-container-type': type });\n button.addEventListener('click', function() {\n if (activeTarget) { addToTarget(button, 'tool'); return; }\n\n var row = createRow();\n var column = row.appendChild(createColumn(MAX_COL_SIZE));\n var container = column.appendChild(definition.create({}));\n\n addNode(type, container, function() {\n canvas.appendChild(row);\n }, { parent: canvas, source: 'tool' });\n });\n addContainerGroup.appendChild(button);\n addButtons.push({ button: button, home: addContainerGroup, group: toolbarGroupOf(definition.group) || 'content' });\n });\n\n // A feature plugin's own buttons, beside the containers': what\n // one makes goes onto the canvas, where the plugin says it belongs.\n // One with align 'end' goes on the right instead, as an icon,\n // beside the source and preview buttons.\n var endItems = [];\n shownToolbar = {};\n Object.keys(FEATURES).forEach(function(name) {\n shownToolbar[name] = toolbarOf(FEATURES[name]);\n shownToolbar[name].forEach(function(item, index) {\n var button = featureButton(name, item, index);\n\n if (item.align === 'end') {\n endItems.push(button);\n } else {\n addContainerGroup.appendChild(button);\n // One that names no category of its own has its plugin's\n addButtons.push({ button: button, home: addContainerGroup, group: toolbarGroupOf(item.group) || name });\n }\n });\n });\n\n // Buttons on right\n layoutDropdown = dom.create('<div class=\"dropdown pull-right ge-layout-mode\">' +\n '<button type=\"button\" class=\"btn btn-sm btn-primary dropdown-toggle\" data-bs-toggle=\"dropdown\"></button>' +\n '<div class=\"dropdown-menu\" role=\"menu\"></div>' +\n '</div>');\n dom.delegate(layoutDropdown, 'click', 'a', function() {\n // Through changeView, so the dropdown and the method are\n // one path rather than two that have to agree\n changeView(this.getAttribute('data-ge-view'));\n });\n wrapper.appendChild(layoutDropdown);\n\n settings.layout_modes.forEach(function(view) {\n dom.one(layoutDropdown, '.dropdown-menu').appendChild(dom.element('a', {\n 'class': 'dropdown-item',\n 'data-ge-view': view,\n title: t(labelKeyFor(view)),\n }, t(labelKeyFor(view))));\n });\n dom.one(layoutDropdown, 'button').textContent = t(labelKeyFor(curView));\n\n var btnGroup = wrapper.appendChild(dom.element('div', { 'class': 'btn-group pull-right' }));\n\n if (settings.edit_source) {\n // Built again by setLocale, maybe with the source open\n var htmlButton = dom.create('<button type=\"button\" class=\"btn btn-sm btn-primary gm-edit-mode\"><i class=\"bi bi-code-slash\"></i></button>');\n htmlButton.setAttribute('title', t('tool.edit_source'));\n dom.toggleClass(htmlButton, 'active btn-danger', sourceOpen);\n htmlButton.addEventListener('click', function() {\n if (sourceOpen) {\n closeSource();\n } else {\n openSource();\n }\n\n dom.toggleClass(htmlButton, 'active btn-danger', sourceOpen);\n });\n btnGroup.appendChild(htmlButton);\n }\n\n var previewButton = dom.create('<button type=\"button\" class=\"btn btn-sm btn-primary gm-preview\"><i class=\"bi bi-eye-fill\"></i></button>');\n var endPreview = function() {\n if (!dom.hasClass(previewButton, 'active')) {\n dom.addClass(canvas, 'ge-editing');\n }\n };\n previewButton.setAttribute('title', t('tool.preview'));\n previewButton.addEventListener('mouseenter', function() {\n dom.removeClass(canvas, 'ge-editing');\n });\n previewButton.addEventListener('click', function() {\n dom.toggleClass(previewButton, 'active btn-danger');\n endPreview();\n });\n previewButton.addEventListener('mouseleave', endPreview);\n btnGroup.appendChild(previewButton);\n\n // Floated right after the source and preview buttons, so it\n // stands to their left. Not a btn-group: its buttons show one at\n // a time, and a hidden one still counts as a neighbour to\n // Bootstrap, which squares off the corners they would share.\n if (endItems.length) {\n var end = wrapper.appendChild(dom.element('div', { 'class': 'pull-right ge-toolbar-end' }));\n endItems.forEach(function(button) { end.appendChild(button); });\n }\n\n if (settings.toolbar_groups) { createGroupTabs(start); }\n if (overflowMenu) { createOverflowMenu(start); }\n\n makeToolbarDraggable();\n }\n\n /** The core's categories, ahead of the plugins' own. */\n var CORE_GROUPS = [\n { name: 'rows', labelKey: 'group.rows' },\n { name: 'content', labelKey: 'group.content' },\n { name: 'elements', labelKey: 'group.elements' },\n ];\n\n /** A plugin's category, when it names one. */\n function toolbarGroupOf(value) {\n return typeof value === 'string' && value.trim() !== '' ? value : null;\n }\n\n /**\n * toolbar_groups: tabs at the start of the toolbar, one per category\n * of add buttons, and only the chosen one's buttons on it. The rest\n * wait in a hidden stash inside the toolbar, so toolbarItems still\n * finds them and the btn-groups round the corners of what shows. With\n * a single category there is nothing to choose, and no tabs.\n */\n function createGroupTabs(start) {\n // The core's two first, then the rest as their first button comes\n var names = CORE_GROUPS.map(function(group) { return group.name; });\n addButtons.forEach(function(entry) {\n if (names.indexOf(entry.group) < 0) { names.push(entry.group); }\n });\n names = names.filter(function(name) {\n return addButtons.some(function(entry) { return entry.group === name; });\n });\n\n if (names.length < 2) { return; }\n\n var tabs = dom.element('div', { 'class': 'ge-toolbar-groups btn-group', role: 'tablist', 'aria-label': t('group.select') });\n start.insertBefore(tabs, start.firstChild);\n var stash = mainControls.appendChild(dom.element('div', { 'class': 'ge-toolbar-stash', hidden: 'hidden' }));\n\n names.forEach(function(name) {\n var tab = tabs.appendChild(dom.element('button', {\n type: 'button',\n 'class': 'btn btn-sm btn-outline-secondary',\n role: 'tab',\n 'data-ge-group': name,\n }, groupLabel(name)));\n\n tab.addEventListener('click', function() { showGroup(name); });\n });\n\n showGroup(names.indexOf(toolbarGroup) >= 0 ? toolbarGroup : names[0]);\n\n function showGroup(name) {\n toolbarGroup = name;\n\n addButtons.forEach(function(entry) {\n (entry.group === name ? entry.home : stash).appendChild(entry.button);\n });\n\n dom.children(tabs).forEach(function(tab) {\n var chosen = tab.getAttribute('data-ge-group') === name;\n dom.toggleClass(tab, 'active', chosen);\n tab.setAttribute('aria-selected', chosen ? 'true' : 'false');\n });\n\n refitToolbar();\n }\n }\n\n /** A category's label: its group.<name> string, or its first button's when it has none. */\n function groupLabel(name) {\n var key = 'group.' + name;\n if (hasString(settings, key)) { return t(key); }\n\n var first = addButtons.filter(function(entry) { return entry.group === name; })[0];\n return first.button.getAttribute('title') || name;\n }\n\n /** The add buttons on the toolbar's line: all of them, or the chosen category's. */\n function shownAddButtons() {\n return addButtons.filter(function(entry) { return !dom.closest(entry.button, '.ge-toolbar-stash'); });\n }\n\n /** The toolbar off the page, with what keeps its overflow menu up to date. */\n /** A feature plugin's toolbar items: its array, or what its function returns now. */\n function toolbarOf(feature) {\n var items = typeof feature.toolbar === 'function' ? feature.toolbar() : feature.toolbar;\n return Array.isArray(items) ? items : [];\n }\n\n /**\n * ge.refreshToolbar(): the toolbar built again, from what the plugins'\n * toolbars hold now - a plugin whose buttons come and go calls it when\n * they have. The category shown, the preview and the source view stay\n * as they are; an open overflow menu folds away.\n */\n function refreshToolbar() {\n // Not built yet - the first one reads the toolbars as they are\n // then - or taken away for good\n if (!mainControls || destroyed) { return; }\n\n var previewing = !!dom.one(mainControls, '.gm-preview.active');\n\n removeMainControls();\n createMainControls();\n\n if (previewing) {\n dom.addClass(dom.one(mainControls, '.gm-preview'), 'active btn-danger');\n }\n onScroll();\n }\n\n function removeMainControls() {\n if (toolbarLifetime) { toolbarLifetime.abort(); }\n toolbarLifetime = null;\n closeOverflowMenu = function() {};\n refitToolbar = function() {};\n mainControls.remove();\n }\n\n /**\n * The add buttons that don't fit on the toolbar's line, behind a\n * button at its end. They are the same buttons, moved rather than\n * copied, so a click, a drag or a plugin finding them with\n * toolbarItems works as it does on the line. Which ones go is worked\n * out again whenever the toolbar or what is on it changes size.\n */\n function createOverflowMenu(start) {\n var more = dom.create('<div class=\"ge-toolbar-more\">' +\n '<button type=\"button\" class=\"btn btn-sm btn-light\"><i class=\"bi bi-three-dots\"></i></button>' +\n '<div class=\"ge-toolbar-overflow\">' +\n '<div class=\"ge-addRowGroup btn-group\"></div>' +\n '<div class=\"ge-addContainerGroup btn-group\"></div>' +\n '</div>' +\n '</div>');\n start.parentNode.insertBefore(more, start.nextSibling);\n\n var toggle = dom.one(more, 'button');\n var panel = dom.one(more, '.ge-toolbar-overflow');\n var spares = dom.all(panel, '.btn-group');\n // The spare group in the menu for each group on the line\n function spareOf(home) {\n return home === addRowGroup ? spares[0] : spares[1];\n }\n\n toggle.setAttribute('title', t('tool.more'));\n toggle.setAttribute('aria-haspopup', 'true');\n toggle.setAttribute('aria-expanded', 'false');\n\n var menuLifetime = toolbarLifetime = new AbortController();\n var signal = { signal: menuLifetime.signal };\n\n toggle.addEventListener('click', function() { openOverflow(!dom.hasClass(more, 'ge-open')); });\n // A button in the menu has done its job once it is clicked\n panel.addEventListener('click', function(e) {\n if (dom.closest(e.target, '[data-ge-toolbar]')) { openOverflow(false); }\n });\n document.addEventListener('pointerdown', function(e) {\n if (!more.contains(e.target)) { openOverflow(false); }\n }, signal);\n document.addEventListener('keydown', function(e) {\n if (e.key === 'Escape') { openOverflow(false); }\n }, signal);\n closeOverflowMenu = function() { openOverflow(false); };\n // A category chosen: another set of buttons to fit\n refitToolbar = fit;\n\n fit();\n\n if (window.ResizeObserver) {\n // Not in the callback itself: moving buttons there would\n // resize what is being observed before the frame is drawn\n var pending = false;\n var observer = new window.ResizeObserver(function() {\n if (pending) { return; }\n pending = true;\n window.requestAnimationFrame(function() {\n pending = false;\n if (!menuLifetime.signal.aborted) { fit(); }\n });\n });\n // The toolbar's width, and the buttons on the right of it\n // showing and hiding, as the paste button does\n observer.observe(wrapper);\n observer.observe(start);\n menuLifetime.signal.addEventListener('abort', function() { observer.disconnect(); });\n }\n\n function openOverflow(open) {\n open = open && dom.hasClass(more, 'ge-needed');\n dom.toggleClass(more, 'ge-open', open);\n toggle.setAttribute('aria-expanded', open ? 'true' : 'false');\n }\n\n /** Back on the line, then the last ones off it until the rest fit. */\n function fit() {\n // Only the chosen category's, with toolbar_groups: the others\n // wait in their stash\n var homes = shownAddButtons();\n homes.forEach(function(entry) { entry.home.appendChild(entry.button); });\n dom.removeClass(more, 'ge-needed');\n\n if (start.scrollWidth <= start.clientWidth) {\n openOverflow(false);\n return;\n }\n\n dom.addClass(more, 'ge-needed');\n for (var i = homes.length - 1; i >= 0 && start.scrollWidth > start.clientWidth; i--) {\n var into = spareOf(homes[i].home);\n into.insertBefore(homes[i].button, into.firstChild);\n }\n }\n }\n\n /**\n * A toolbar button's face: the plugin's icon alone when it has one,\n * with its label as the title, or a plus and the label otherwise.\n */\n function labelButton(button, label, iconClass) {\n button.setAttribute('title', label);\n\n if (iconClass) {\n button.appendChild(dom.element('i', { 'class': iconClass }));\n return button;\n }\n\n button.appendChild(dom.create('<i class=\"bi bi-plus\"></i>'));\n button.appendChild(dom.element('span', {}, label));\n return button;\n }\n\n /** A feature plugin's toolbar button. At the end it is always an icon, `bi bi-plus` if it has none of its own. */\n function featureButton(name, item, index) {\n var iconClass = item.iconClass || (item.align === 'end' ? 'bi bi-plus' : null);\n // A label of its own, worked out when the toolbar is built - and\n // built again by setLocale - or the string its labelKey names\n var label = typeof item.label === 'function' ? item.label() : (item.label || t(item.labelKey));\n // Grey with the add buttons on the left, blue with the source and\n // preview buttons on the right\n var colour = item.align === 'end' ? 'btn-primary' : 'btn-light';\n var button = labelButton(dom.element('a', { 'class': 'btn btn-sm ' + colour + ' ge-add-container ge-add-feature' }), label, iconClass);\n\n dom.addClass(button, item.className || '');\n dom.attr(button, {\n 'data-ge-toolbar': 'feature',\n 'data-ge-feature': name,\n 'data-ge-item': index,\n });\n button.addEventListener('click', function() {\n if (activeTarget) { addToTarget(button, item.source || 'tool'); return; }\n\n var made = item.create();\n // A plugin that could not make one says so with null\n if (!made) { return; }\n\n // One that belongs in a column brings a row and a column\n // of its own, the way a container does\n var placed = item.inColumn ? inRowOfItsOwn(made) : made;\n\n var added = addNode(item.kind, made, function() {\n canvas.appendChild(placed);\n }, { parent: canvas, source: item.source || 'tool' });\n\n if (added && item.inColumn && placed.scrollIntoView) {\n placed.scrollIntoView({behavior: 'smooth'});\n }\n });\n\n return button;\n }\n\n /**\n * The toolbar's buttons as a palette: drag one onto the canvas and\n * what it makes is created where it lands, rather than at the end.\n *\n * On by default in the mode where everything else is dragged by its\n * body rather than by a handle, since that is the same idea applied to\n * the toolbar; toolbar_drag: true or false decides it outright.\n */\n function toolbarDrags() {\n if (settings.toolbar_drag === 'auto') { return settings.drag_handle === 'drawer'; }\n\n return !!settings.toolbar_drag;\n }\n\n function makeToolbarDraggable() {\n var buttons = dom.all(mainControls, '[data-ge-toolbar]');\n\n buttons.forEach(function(button) {\n dom.removeClass(button, 'ge-palette-button');\n button.removeEventListener('pointerdown', startToolbarDrag);\n });\n\n if (!toolbarDrags()) { return; }\n\n buttons.forEach(function(button) {\n dom.addClass(button, 'ge-palette-button');\n button.addEventListener('pointerdown', startToolbarDrag);\n });\n }\n\n /**\n * A toolbar button carried onto the canvas.\n *\n * Nothing happens until the pointer has moved far enough to mean it:\n * below that the gesture is a click, and the button's own handler\n * adds the block at the end of the canvas as it always has - which is\n * also what keeps the add column tool's hold-to-pick working.\n */\n function startToolbarDrag(e) {\n var button = e.currentTarget;\n var startX = e.pageX;\n var startY = e.pageY;\n var helper = null;\n\n if (e.button) { return; }\n\n function far(move) {\n return Math.abs(move.pageX - startX) + Math.abs(move.pageY - startY) >\n settings.drag.threshold;\n }\n\n function onMove(move) {\n if (!helper) {\n if (!far(move)) { return; }\n\n helper = dom.addClass(button.cloneNode(true), 'ge-toolbar-helper');\n document.body.appendChild(helper);\n // The menu a button came from would hide where it lands\n closeOverflowMenu();\n dom.addClass(canvas, 'ge-dropping');\n }\n\n dom.css(helper, { left: move.pageX - 14, top: move.pageY - 14 });\n showDropMarker(move.pageX, move.pageY);\n }\n\n function onUp(up) {\n document.removeEventListener('pointermove', onMove);\n dom.off(document, 'pointerup pointercancel', onUp);\n\n if (!helper) { return; }\n\n helper.remove();\n dom.removeClass(canvas, 'ge-dropping');\n hideDropMarker();\n\n // The click that follows a drag would add the block a second\n // time, at the end of the canvas. Caught on the way down, so\n // it never reaches the button's own handler.\n var swallow = function(click) {\n if (click.target !== button && !button.contains(click.target)) { return; }\n click.preventDefault();\n click.stopImmediatePropagation();\n };\n window.addEventListener('click', swallow, { capture: true, once: true });\n // A drag the browser does not follow with a click leaves\n // nothing to swallow: the next click is a click\n window.setTimeout(function() { window.removeEventListener('click', swallow, { capture: true }); }, 0);\n\n var where = dropPlaceAt(up.pageX, up.pageY);\n if (where) { insertFromToolbar(button, where); }\n }\n\n // On the document, not on the button: until the gesture is far\n // enough along to be a drag there is nothing to capture the\n // pointer with, and the pointer has left the button by then\n document.addEventListener('pointermove', onMove);\n dom.on(document, 'pointerup pointercancel', onUp);\n }\n\n /**\n * Where a drop at this point would put things: which region it lands\n * in, and which of that region's children it goes before.\n *\n * Worked out from the pointer rather than handed to a sortable. The\n * canvas is a tree of regions that connected sortables fight over -\n * a column grows as a placeholder is put in it, until it covers the\n * pointer wherever the pointer goes - and a new block has one\n * question to answer, which is where it lands.\n */\n function dropPlaceAt(pageX, pageY) {\n var x = pageX - window.scrollX;\n var y = pageY - window.scrollY;\n var under = document.elementFromPoint(x, y);\n\n if (!under) { return null; }\n\n var region = dom.closest(under, ['.column', '.ge-canvas'].concat(pluginHooks('regions')).join(', '));\n if (!region || (region !== canvas && !canvas.contains(region))) {\n return null;\n }\n\n var before = null;\n\n dom.children(region, blockSelector()).forEach(function(block) {\n if (before) { return; }\n\n var box = block.getBoundingClientRect();\n if (y < box.top + box.height / 2) { before = block; }\n });\n\n return { region: region, before: before };\n }\n\n /**\n * A feature's toolbar button dropped on the canvas. A region that will\n * not have what it makes - a section dropped on a column - gives way\n * to the canvas, just after the top level block the pointer was in.\n */\n function insertFeatureFromToolbar(button, where, source) {\n // The item the button was built from, whatever the plugin's list\n // says now: it may have changed since, and the toolbar not yet\n var item = (shownToolbar[button.getAttribute('data-ge-feature')] || [])[parseInt(button.getAttribute('data-ge-item'), 10)];\n if (!item) { return null; }\n var made = item.create();\n if (!made) { return null; }\n var placed = made;\n\n if (item.inColumn) {\n // Where it lands in a column, or in a row and a column of its\n // own anywhere else\n if (!dom.is(where.region, '.column')) { placed = inRowOfItsOwn(made); }\n } else if (!acceptsBlock(where.region, made)) {\n var ancestors = where.region === canvas ? [] : dom.parentsUntil(where.region, canvas).reverse().concat([where.region]);\n var top = ancestors[0] || null;\n where = { region: canvas, before: top ? top.nextElementSibling : null };\n }\n\n return addNode(item.kind, made, function() {\n if (where.before) {\n where.before.parentNode.insertBefore(placed, where.before);\n } else {\n where.region.appendChild(placed);\n }\n }, { parent: where.region, source: item.source || source || 'dragdrop' });\n }\n\n /** A detached row with one full width column holding `node`. */\n function inRowOfItsOwn(node) {\n var row = createRow();\n row.appendChild(createColumn(MAX_COL_SIZE)).appendChild(node);\n\n return row;\n }\n\n /** A line where the block would go, following the pointer. */\n function showDropMarker(pageX, pageY) {\n var where = dropPlaceAt(pageX, pageY);\n\n if (!where) { return hideDropMarker(); }\n\n if (!dropMarker) { dropMarker = dom.element('div', { 'class': 'ge-drop-marker' }); }\n\n if (where.before) {\n where.before.parentNode.insertBefore(dropMarker, where.before);\n } else {\n where.region.appendChild(dropMarker);\n }\n\n return undefined;\n }\n\n function hideDropMarker() {\n if (dropMarker) { dropMarker.remove(); }\n }\n\n /**\n * The row or container a toolbar button stands for, made and put where\n * the pointer left it.\n */\n function insertFromToolbar(button, where, source) {\n if (button.getAttribute('data-ge-toolbar') === 'feature') {\n return insertFeatureFromToolbar(button, where, source);\n }\n\n var container = button.getAttribute('data-ge-toolbar') === 'container';\n var type = button.getAttribute('data-ge-container-type');\n var made = container\n ? CONTAINERS[type].create({})\n : rowFromLayout(button.getAttribute('data-ge-layout'));\n\n // A container belongs in a column: dropped straight onto the\n // canvas it brings a row and a column of its own\n var placed = made;\n if (container && !dom.is(where.region, '.column')) { placed = inRowOfItsOwn(made); }\n\n return addNode(container ? type : 'row', made, function() {\n if (where.before) {\n where.before.parentNode.insertBefore(placed, where.before);\n } else {\n where.region.appendChild(placed);\n }\n }, { parent: where.region, source: source || 'dragdrop' });\n }\n\n /**\n * The column width as a utility family, so the Responsive section of\n * a column's panel has a field for it: every size, units or not, in\n * the view being edited. A write is a resize, through the resize\n * events, not a utility change.\n */\n function widthFamily() {\n var values = [];\n for (var units = 1; units <= MAX_COL_SIZE; units++) { values.push(String(units)); }\n\n return {\n name: 'col',\n values: values.concat(FLEX_SIZES),\n appliesTo: ['column'],\n labelKey: 'utility.col_width',\n className: function(key, value) { return sizeClass(breakpoint(key), parseSize(value)); },\n choices: function() { return settings.valid_col_sizes.map(String); },\n label: function(value) {\n if (value === 'equal') { return t('utility.col_equal'); }\n if (value === 'auto') { return t('utility.col_auto'); }\n\n return value;\n },\n write: function(col, value, view, source) {\n return resizeColumn(col, value === null ? null : parseSize(value), source, view);\n },\n // With no size of its own, a column in a row with row-cols\n // takes its share from the row, which the field says\n blank: function(col, view) {\n var winner = view === ALL_VIEW ? null : rowColsWinner(col, breakpoint(view));\n return winner ? t('utility.col_from_row', { count: rowColsLabel(winner.value) }) : null;\n },\n };\n }\n\n /** A size as markup or a select carries it: '4' is 4, 'equal' and 'auto' are themselves. */\n function parseSize(size) {\n return /^\\d+$/.test(String(size)) ? parseInt(size, 10) : size;\n }\n\n /** A row from a toolbar button's data-ge-layout: sizes, or a row-cols layout as JSON. */\n function rowFromLayout(layout) {\n if (/^\\s*\\{/.test(layout || '')) { return rowFromLayoutValue(JSON.parse(layout)); }\n\n return rowFromLayoutValue((layout || '').split(',').filter(function(size) {\n return size !== '';\n }).map(parseSize));\n }\n\n /**\n * A row from a layout: an array of sizes, or { row_cols, columns } -\n * row-cols per breakpoint, and that many columns sized by the row.\n */\n function rowFromLayoutValue(layout) {\n var row = createRow();\n\n if (Array.isArray(layout)) {\n layout.forEach(function(size) { row.appendChild(createColumn(size)); });\n return row;\n }\n\n Object.keys(layout.row_cols || {}).forEach(function(key) {\n var value = layout.row_cols[key];\n var tier = breakpoint(key);\n if (tier && ROW_COLS_VALUES.indexOf(String(value)) !== -1) { dom.addClass(row, rowColsClass(tier, value)); }\n });\n\n for (var i = 0; i < (layout.columns || 0); i++) { row.appendChild(createColumn(null)); }\n\n return row;\n }\n\n /** \"1, md: 3\": a row-cols layout's counts, for its button's title. */\n function rowColsText(counts) {\n return BREAKPOINTS.filter(function(tier) { return counts && counts[tier.key] !== undefined; })\n .map(function(tier) { return (tier.infix ? tier.key + ': ' : '') + counts[tier.key]; })\n .join(', ');\n }\n\n /** The icon of a row-cols layout: one line of equal columns, as many as its widest count. */\n function rowColsIcon(layout) {\n var widest = 1;\n Object.keys(layout.row_cols || {}).forEach(function(key) {\n var value = layout.row_cols[key];\n if (value !== 'auto') { widest = Math.max(widest, parseInt(value, 10) || 1); }\n });\n\n return Array.apply(null, Array(Math.min(widest, layout.columns || widest))).map(function() { return 'equal'; });\n }\n\n function onScroll() {\n var scrollTop = window.pageYOffset;\n\n if (\n scrollTop > dom.offset(mainControls).top &&\n scrollTop < dom.offset(canvas).top + dom.contentHeight(canvas)\n ) {\n if (dom.hasClass(wrapper, 'ge-top')) {\n dom.css(wrapper, {\n left: dom.offset(wrapper).left,\n width: dom.outerWidth(wrapper),\n });\n dom.removeClass(wrapper, 'ge-top');\n dom.addClass(wrapper, 'ge-fixed');\n }\n } else {\n if (dom.hasClass(wrapper, 'ge-fixed')) {\n dom.css(wrapper, { left: '', width: '' });\n dom.removeClass(wrapper, 'ge-fixed');\n dom.addClass(wrapper, 'ge-top');\n }\n }\n }\n\n /**\n * A click on the host's plain content makes it a text: of the one\n * editor offered, or of the one chosen when there are several. What\n * a click on a text does is its editor plugin's business.\n */\n function onContentClick() {\n var block = this;\n if (block.getAttribute('data-ge-content-type')) { return; }\n\n // A second click, with the choice still open, withdraws it\n if (closeSizePicker()) { return; }\n\n // Content nobody can see - a tab that is not the open one, a\n // closed accordion item - has no geometry for an editor to lay\n // its toolbar out against, and nothing anyone can type into\n if (!dom.visible(block)) { return; }\n\n var offers = textOffers();\n if (!offers.length) { return; }\n\n if (offers.length === 1) {\n convertPlain(block, offers[0]);\n } else {\n openConvertPicker(block, offers);\n }\n }\n\n /**\n * Plain content made a text of `offer`'s type, through the convert\n * events: the type goes on, and the plugin that declared it takes the\n * block over and opens its editor. Nothing else about the node\n * changes. False when the library is missing or a handler canceled.\n */\n function convertPlain(block, offer) {\n // Not converted, so the next click tries again: the library may\n // be loaded by then\n if (offer.available && !offer.available()) {\n if (offer.missingKey) { console.error(t(offer.missingKey)); }\n return false;\n }\n\n return operate(function() {\n var payload = payloadFor('plain', block, { source: 'tool', from: 'plain', to: offer.type });\n\n if (!emit('before-convert', payload)) { return false; }\n\n dom.addClass(block, 'ge-content-type-' + offer.type);\n block.setAttribute('data-ge-content-type', offer.type);\n\n // Its plain drawer goes: the block is the plugin's now, and\n // the plugin gives it the drawer a text has\n var textBlock = block.parentElement;\n if (dom.hasClass(textBlock, 'ge-text-block')) {\n dom.removeClass(textBlock, 'ge-plain-block');\n dom.children(textBlock, '.ge-tools-drawer').forEach(function(drawer) { drawer.remove(); });\n }\n\n emit('after-convert', payload);\n offer.edit(block);\n\n return true;\n });\n }\n\n /**\n * The text types offered, as a strip under the plain content's\n * drawer, when there is more than one to choose from.\n */\n function openConvertPicker(block, offers) {\n var textBlock = dom.hasClass(block.parentElement, 'ge-text-block') ? block.parentElement : null;\n if (!textBlock) { return; }\n\n openPicker(dom.child(textBlock, '.ge-tools-drawer'), offers.map(function(offer) {\n return {\n label: offer.label,\n title: t('tool.convert_type', { editor: offer.label }),\n attributes: { 'data-ge-content-type': offer.type },\n choose: function() { convertPlain(block, offer); },\n };\n }), 'ge-text-picker ge-convert-picker', textBlock);\n }\n\n /**\n * A choice as a strip under `anchor` - a tool, or a drawer - one\n * button per `{ label, title, attributes, choose }`. Leaving `hover`\n * (the anchor by default) withdraws it, and so does closeSizePicker.\n */\n function openPicker(anchor, choices, className, hover) {\n closeSizePicker();\n if (!anchor) { return; }\n\n var drawer = dom.closest(anchor, '.ge-tools-drawer');\n if (drawer) { dom.addClass(drawer, 'ge-picker-open'); }\n sizePicker = anchor.appendChild(dom.addClass(dom.element('div', { 'class': 'ge-size-picker' }), className || ''));\n\n choices.forEach(function(choice) {\n var button = dom.attr(dom.element('a', { 'class': 'ge-size ge-size-flex' }), choice.attributes || {});\n\n button.setAttribute('title', choice.title || choice.label);\n button.textContent = choice.label;\n button.addEventListener('click', function(e) {\n e.preventDefault();\n e.stopPropagation();\n\n closeSizePicker();\n choice.choose();\n });\n sizePicker.appendChild(button);\n });\n\n withdrawOnLeave(hover || anchor);\n }\n\n /** Leaving `node` withdraws the picker open under it, unless the pointer went into the picker. */\n function withdrawOnLeave(node) {\n node.addEventListener('mouseleave', function() {\n window.setTimeout(function() {\n if (sizePicker && !sizePicker.matches(':hover')) { closeSizePicker(); }\n }, 400);\n }, { once: true });\n }\n\n /**\n * Every text type the feature plugins declare, in the order they\n * were registered: the first plugin to declare a type owns it.\n */\n function textTypes() {\n var owners = {};\n var entries = [];\n\n Object.keys(FEATURES).forEach(function(name) {\n var feature = FEATURES[name];\n if (!feature.textTypes) { return; }\n\n (feature.textTypes() || []).forEach(function(entry) {\n if (owners[entry.type]) {\n if (owners[entry.type] !== name) {\n warnOnceHere('text-type:' + entry.type, 'the \"' + name + '\" plugin declares the ' +\n 'text type \"' + entry.type + '\", which the \"' + owners[entry.type] +\n '\" plugin already declares: ignored');\n }\n return;\n }\n\n owners[entry.type] = name;\n entries.push(entry);\n });\n });\n\n return entries;\n }\n\n /** The types plain content can be made, in order: the ones not marked `offered: false`. */\n function textOffers() {\n return textTypes().filter(function(entry) { return entry.offered !== false; });\n }\n\n /** Whether a plugin declares this text type. */\n function hasTextOwner(type) {\n return textTypes().some(function(entry) { return entry.type === type; });\n }\n\n function reset() {\n deinit();\n init();\n }\n\n /**\n * The canvas as html, in the textarea in its place, to edit by hand.\n * A feature plugin's onSourceOpen may put a code editor over the\n * textarea; its onSourceClose puts what it holds back in it, which is\n * what the canvas is made of again.\n */\n function openSource() {\n deinit();\n // The canvas is made again from the html when it comes back\n changeTarget(null);\n changeSelection(null);\n htmlTextArea.style.height = (0.8 * document.documentElement.clientHeight) + 'px';\n htmlTextArea.value = canvas.innerHTML;\n dom.show(htmlTextArea);\n dom.hide(canvas);\n sourceOpen = true;\n plugins('onSourceOpen', htmlTextArea);\n }\n\n /**\n * The textarea's html back into the canvas. innerHTML, so a <script>\n * typed into the source is markup like any other and does not run in\n * the editor; the page it is published on runs it.\n */\n function closeSource() {\n plugins('onSourceClose', htmlTextArea);\n sourceOpen = false;\n dom.setHtml(canvas, htmlTextArea.value);\n dom.show(canvas);\n init();\n dom.hide(htmlTextArea);\n }\n\n /**\n * What can be the active target: a column, or a plugin's region - a\n * section. Not the canvas, which is where the toolbar adds without one.\n */\n function targetSelector() {\n return ['.column'].concat(pluginHooks('regions')).join(', ');\n }\n\n function isTarget(node) {\n return !!node && node !== canvas && canvas.contains(node) && dom.is(node, targetSelector());\n }\n\n /** The one way the active target changes, told only when it does. */\n function changeTarget(node) {\n if (node === activeTarget) { return; }\n\n var from = activeTarget;\n if (from) { dom.removeClass(from, 'ge-active-target'); }\n activeTarget = node;\n if (node && dom.hasClass(canvas, 'ge-editing')) { dom.addClass(node, 'ge-active-target'); }\n\n emit('target-change', { canvas: canvas, target: node, from: from });\n }\n\n /**\n * A toolbar button's click with an active target: what it makes goes\n * where a drop at the target's end would put it.\n */\n function addToTarget(button, source) {\n var made = insertFromToolbar(button, { region: activeTarget, before: null }, source);\n if (made && made.scrollIntoView) { made.scrollIntoView({ behavior: 'smooth' }); }\n }\n\n function init() {\n // The node whose settings were open is gone - deleted, say - and\n // its panel with it\n if (openSettingsState && !dom.attached(openSettingsState.node)) {\n closeSettings();\n }\n // The same for the selected node, which the sidebar stops showing\n if (selected && !canvas.contains(selected)) {\n changeSelection(null);\n }\n // And a dialog showing part of a panel that is gone\n if (dialogState && dialogState.home && !dom.attached(dialogState.home)) {\n closeDialog();\n }\n\n runFilter(true);\n dom.addClass(canvas, 'ge-editing');\n dom.toggleClass(canvas, 'ge-drag-drawer', settings.drag_handle === 'drawer');\n addAllColClasses();\n var cutter = textCutter();\n splitTexts(cutter);\n wrapContent(cutter);\n wrapTexts();\n createRowControls();\n createColControls();\n markContainers();\n plugins('onInit');\n makeSortable();\n makeResizable();\n switchLayout(curView);\n refreshPreviews(canvas);\n\n // Deleted, or taken out some other way, it is a target no more\n if (activeTarget && !canvas.contains(activeTarget)) {\n changeTarget(null);\n } else if (activeTarget) {\n dom.addClass(activeTarget, 'ge-active-target');\n }\n\n showSidebar();\n }\n\n function deinit() {\n // Its panel goes home to its drawer first, and both go together\n closeSettings();\n hideSidebar();\n dom.removeClass(canvas, 'ge-editing ge-drag-drawer ge-dropping');\n // The mark goes, the target stays: getHtml comes straight back\n if (activeTarget) { dom.removeClass(activeTarget, 'ge-active-target'); }\n // Before the drawers and the text blocks come off: an editor\n // plugin closes its editors here, and finds them where it left them\n plugins('onBeforeDeinit');\n closeSizePicker();\n hideDropMarker();\n // In case a dialog was opened with no settings panel open\n closeDialog();\n removeDrawers(canvas);\n pluginFields.clear();\n unwrapTexts(canvas);\n plugins('onDeinit');\n // After the rich text editors have let go of their content areas:\n // one that rebuilt its area's DOM brought the preview styles back\n // with it, and the attribute recording them came back too\n clearPreviews(canvas);\n clearRowCols(canvas);\n unmarkContainers();\n removeSortable();\n removeResizable();\n runFilter(false, canvas);\n }\n\n function removeDrawers(root) {\n dom.all(root, '.ge-tools-drawer').forEach(function(drawer) { drawer.remove(); });\n }\n\n function clearRowCols(root) {\n dom.all(root, '[data-ge-row-cols]').forEach(function(row) { row.removeAttribute('data-ge-row-cols'); });\n }\n\n /**\n * The plugins that cannot be read without the canvas leaving editing:\n * the ones that put something on the canvas - an unmark, an onDeinit\n * or an onBeforeDeinit takes it off - and say nothing of how to take\n * it off a copy.\n */\n function pluginsWithoutCleanMarkup() {\n var names = [];\n\n [CONTAINERS, FEATURES, UTILITIES].forEach(function(registry) {\n Object.keys(registry).forEach(function(name) {\n var plugin = registry[name];\n var marks = plugin.unmark || plugin.onDeinit || plugin.onBeforeDeinit;\n if (marks && !plugin.cleanMarkup) { names.push(name); }\n });\n });\n\n return names;\n }\n\n /**\n * A copy of the canvas, and the way from each of its elements back to\n * the one it was copied from. The two trees are walked side by side,\n * which works because a deep clone has the same shape.\n */\n function copyCanvas() {\n var copy = canvas.cloneNode(true);\n var toLive = new Map();\n var toCopy = new Map();\n var live = document.createTreeWalker(canvas, NodeFilter.SHOW_ELEMENT);\n var copied = document.createTreeWalker(copy, NodeFilter.SHOW_ELEMENT);\n var a = live.currentNode;\n var b = copied.currentNode;\n\n while (a && b) {\n toLive.set(b, a);\n toCopy.set(a, b);\n a = live.nextNode();\n b = copied.nextNode();\n }\n\n return {\n root: copy,\n liveOf: function(node) { return toLive.get(node) || null; },\n copyOf: function(node) { return toCopy.get(node) || null; },\n };\n }\n\n /**\n * getHtml without the canvas leaving editing: what deinit takes off,\n * taken off a copy, so the text being typed into, the settings panel\n * and the focus are where they were. The same markup getHtml gives,\n * or getHtml itself - with a word, once - when a plugin can only take\n * its marking off the canvas, or will not this time.\n */\n function snapshotHtml() {\n // Nothing is being edited to keep: the canvas is out of editing\n if (sourceOpen) { return getHtml(); }\n\n var missing = pluginsWithoutCleanMarkup();\n if (missing.length) {\n missing.forEach(function(name) {\n warnOnceHere('snapshot:' + name, 'the \"' + name + '\" plugin has no cleanMarkup, so the canvas ' +\n 'leaves editing to be read: open texts and settings panels close');\n });\n return getHtml();\n }\n\n var copy = copyCanvas();\n var root = copy.root;\n\n [root].concat(dom.all(root, '.ge-active-target, .ge-settings-target')).forEach(function(node) {\n dom.removeClass(node, 'ge-active-target ge-settings-target');\n dom.dropEmptyClass(node);\n });\n dom.all(root, '.ge-drop-marker').forEach(function(marker) { marker.remove(); });\n removeDrawers(root);\n unwrapTexts(root);\n\n var refused = null;\n [CONTAINERS, FEATURES, UTILITIES].forEach(function(registry) {\n Object.keys(registry).forEach(function(name) {\n var plugin = registry[name];\n if (refused || !plugin.cleanMarkup) { return; }\n if (plugin.cleanMarkup(root, copy.liveOf) === false) { refused = name; }\n });\n });\n\n if (refused) {\n warnOnceHere('snapshot-refused:' + refused, 'the \"' + refused + '\" plugin cannot take its marking off ' +\n 'a copy right now, so the canvas leaves editing to be read');\n return getHtml();\n }\n\n clearPreviews(root);\n clearRowCols(root);\n dom.all(root, '[data-ge-container]').forEach(unmarkContainerClasses);\n sortables.forEach(function(sortableInstance) {\n var list = copy.copyOf(sortableInstance.el);\n if (list) { dom.all(list, '[draggable]').forEach(function(node) { node.removeAttribute('draggable'); }); }\n });\n removeResizeFurniture(root);\n runFilter(false, root);\n stripPixelWidths(root);\n\n return root.innerHTML;\n }\n\n /**\n * The markup as a host would save it: no drawers, no editor, no\n * sortables. The canvas goes back to editing afterwards.\n */\n function getHtml(options) {\n if (options && options.keepEditing) { return snapshotHtml(); }\n\n deinit();\n stripPixelWidths(canvas);\n var html = canvas.innerHTML;\n init();\n return html;\n }\n\n /**\n * One node's markup, as getHtml would give it: the canvas goes out of\n * editing to read it and comes back, as it does for getHtml.\n */\n function nodeHtml(node) {\n deinit();\n stripPixelWidths(node);\n var html = node.outerHTML;\n init();\n return html;\n }\n\n /** getHtml with grid-editor's own classes and attributes taken off. */\n function getPlainHtml(options) {\n return plainHtml(getHtml(options));\n }\n\n /**\n * ge.setHtml(): the canvas made of other markup, and edited again. Not\n * an add or a delete of anything, so no events: what was there is\n * replaced as a whole. innerHTML, as the source view does, so a\n * <script> in it is markup and does not run in the editor.\n */\n function setHtml(html) {\n // What is in the textarea is not wanted - html replaces it - but\n // the source view closes the one way it always does\n if (sourceOpen) {\n closeSource();\n if (mainControls) {\n dom.all(mainControls, '.gm-edit-mode').forEach(function(button) {\n dom.removeClass(button, 'active btn-danger');\n });\n }\n }\n\n deinit();\n dom.setHtml(canvas, html);\n init();\n }\n\n /**\n * Take the editor off the canvas: the markup stays, as getHtml would\n * give it, and everything the editor added - controls, panels,\n * listeners - goes. Safe on a canvas already taken out of the page,\n * as a framework tearing a component down does.\n */\n function destroy() {\n // First, while the editor is whole: a plugin may still read it\n plugins('onDestroy');\n // The html being edited is what the canvas is left with\n if (sourceOpen) { closeSource(); }\n deinit();\n activeTarget = null;\n selected = null;\n if (sidebarHolder === instance) { sidebarHolder = null; }\n removeConfirmModal();\n removeSettingsPanels();\n removeDialog();\n removeMainControls();\n htmlTextArea.remove();\n lifetime.abort();\n instances.delete(canvas);\n destroyed = true;\n }\n\n /**\n * The plugins this editor is using: the ones registered by the files\n * the page loaded, narrowed by the plugins setting.\n *\n * Each is a factory, called once here with the handle it works\n * through. Everything a plugin needs from the editor goes through\n * that handle, because the closure it runs outside of is not\n * something it can see.\n */\n function loadPlugins() {\n var api = pluginHandle = pluginApi();\n\n registerFamily('grid', {}, widthFamily());\n if (settings.row_cols !== false) { registerFamily('grid', {}, rowColsFamily()); }\n var wanted = function(name) {\n return !settings.plugins || settings.plugins.indexOf(name) !== -1;\n };\n\n // What the plugins setting does not choose: the text editors,\n // which content_types chooses. A page that names its containers\n // there has named no editor, and still wants the one it uses.\n var featureWanted = function(name, factory) {\n return factory.always === true || wanted(name);\n };\n\n Object.keys(GridEditor.containers).forEach(function(type) {\n if (wanted(type)) { CONTAINERS[type] = GridEditor.containers[type](api); }\n });\n\n Object.keys(GridEditor.features).forEach(function(name) {\n var factory = GridEditor.features[name];\n if (featureWanted(name, factory)) { FEATURES[name] = factory(api); }\n });\n\n Object.keys(GridEditor.utilities).forEach(function(name) {\n if (!wanted(name)) { return; }\n\n UTILITIES[name] = GridEditor.utilities[name](api);\n (UTILITIES[name].families || []).forEach(function(family) {\n registerFamily(name, UTILITIES[name], family);\n });\n });\n\n Object.keys(FEATURES).forEach(function(name) {\n var methods = FEATURES[name].methods || {};\n Object.keys(methods).forEach(function(method) {\n featureMethods[method] = methods[method];\n });\n });\n\n (settings.plugins || []).forEach(function(name) {\n if (CONTAINERS[name] || FEATURES[name] || UTILITIES[name]) { return; }\n\n warnOnceHere('plugin:' + name, 'the \"' + name + '\" plugin is not loaded: ' +\n 'include dist/plugins/grideditor.' + name + '.js after the editor');\n });\n }\n\n /**\n * A hook every loaded plugin may have. Containers first, since a\n * feature that looks at the canvas - elements, say - wants the\n * containers already marked, and utilities last, since they decorate\n * nodes the other two may have just made.\n */\n function plugins(hook, argument) {\n [CONTAINERS, FEATURES, UTILITIES].forEach(function(registry) {\n Object.keys(registry).forEach(function(name) {\n if (registry[name][hook]) { registry[name][hook](argument); }\n });\n });\n }\n\n /** What a plugin is handed. See docs/plugins.md. */\n function pluginApi() {\n return {\n canvas: canvas,\n settings: settings,\n t: t,\n warn: warn,\n containerId: containerId,\n defaultRegion: defaultRegion,\n createTool: createTool,\n createMoveTool: createMoveTool,\n addSettingsTool: addSettingsTool,\n deleteNode: deleteNode,\n place: place,\n createPaneControls: createPaneControls,\n makeLabelEditable: makeLabelEditable,\n labelIn: labelIn,\n unwrapLabels: unwrapLabels,\n suspendToggles: suspendToggles,\n resumeToggles: resumeToggles,\n emit: emit,\n payloadFor: payloadFor,\n operate: operate,\n kindOf: kindOf,\n view: getView,\n viewTiers: function() {\n return tiersFor(curView).map(function(tier) { return tier.key; });\n },\n breakpoints: BREAKPOINTS.map(function(tier) { return tier.key; }),\n getUtility: getUtility,\n setUtility: setUtility,\n utilityField: utilityField,\n bareStyle: bareStyle,\n // The host's own style, under the preview\n hostStyle: hostStyle,\n setHostStyle: setHostStyle,\n // A modal of the editor's own, over the settings\n openDialog: openDialog,\n closeDialog: closeDialog,\n rowFromLayout: rowFromLayoutValue,\n nodeHtml: nodeHtml,\n // The markup as getHtml gives it, with the canvas left editing\n snapshotHtml: snapshotHtml,\n setHtml: setHtml,\n // A question in the editor's confirm modal\n confirm: confirmWith,\n // A text editor has rewritten a content area, so whatever the\n // editor and its plugins had put in there goes back in\n textReady: textReady,\n // A choice under a tool, offered by holding it\n attachPicker: attachPicker,\n openPicker: openPicker,\n closePicker: closeSizePicker,\n // A node's settings panel, in its drawer or open outside it\n detailsOf: detailsOf,\n // A node's drawer: its first child, or for a content area the\n // one beside it in its text block\n drawerOf: drawerOf,\n // The toolbar built again, from the plugins' toolbars as they are now\n refreshToolbar: refreshToolbar,\n toolbarItems: function(name) {\n return mainControls\n ? dom.all(mainControls, '[data-ge-toolbar=\"feature\"][data-ge-feature=\"' + name + '\"]')\n : [];\n },\n };\n }\n\n function drawerOf(node) {\n if (dom.hasClass(node, 'ge-content')) {\n var textBlock = node.parentElement;\n return dom.hasClass(textBlock, 'ge-text-block') ? dom.child(textBlock, '.ge-tools-drawer') : null;\n }\n\n return dom.child(node, '.ge-tools-drawer');\n }\n\n /* --------------------------------------------------------------\n * Utilities: Bootstrap's responsive utility classes.\n *\n * A utility plugin declares families - order, d, justify-content -\n * and this is everything that reads or writes one. Every family is\n * spelled the way Bootstrap spells them all, {prefix}-{infix}-{value}\n * with no infix at the smallest tier, and cascades the way the size\n * classes do: a tier that says nothing takes the nearest smaller one.\n *\n * The canvas cannot show a breakpoint's utilities by itself. A\n * per-breakpoint view narrows the canvas, not the viewport, and\n * Bootstrap's utilities answer to the viewport with !important. So\n * each node gets what its classes mean at the view being edited,\n * as inline !important styles, recorded in an attribute so they come\n * off again - exactly those, leaving the host's own style alone.\n * -------------------------------------------------------------- */\n\n var FAMILIES = {}; // Every family the utility plugins declare, by name\n var UTILITY_NODES = '.row, .column, .ge-content, .ge-element, [data-ge-container]';\n var PREVIEW_ATTR = 'data-ge-preview';\n var utilitiesOpen = false; // Whether the panels show their Responsive section unfolded\n\n function registerFamily(pluginName, utility, family) {\n var name = family.name || family.prefix;\n\n if (FAMILIES[name]) {\n warn('the \"' + pluginName + '\" plugin declares the utility \"' + name +\n '\", which the \"' + FAMILIES[name].plugin + '\" plugin already declared: ignored');\n return;\n }\n\n FAMILIES[name] = {\n plugin: pluginName,\n family: Object.assign({}, family, {\n name: name,\n values: family.values.map(String),\n appliesTo: family.appliesTo || utility.appliesTo || ['row', 'column'],\n }),\n };\n }\n\n /** The family a caller named, or null and a warning when no plugin declares it. */\n function familyNamed(name, method) {\n if (FAMILIES[name]) { return FAMILIES[name].family; }\n\n warnOnceHere('utility:' + name, method + '(' + JSON.stringify(name) + '): no loaded ' +\n 'plugin declares that utility');\n return null;\n }\n\n /**\n * Whether a family applies to a kind of node. A container answers to\n * `container` and to its own type, so a plugin can take them all or\n * name the ones it means.\n */\n function appliesTo(family, kind) {\n // The host's plain content reads and previews its utilities as a\n // text does; with no gear, nothing in its drawer writes them\n if (kind === 'plain') { kind = 'text'; }\n if (family.appliesTo.indexOf(kind) !== -1) { return true; }\n\n return !!CONTAINERS[kind] && family.appliesTo.indexOf('container') !== -1;\n }\n\n function familiesFor(kind) {\n return Object.keys(FAMILIES).map(function(name) {\n return FAMILIES[name].family;\n }).filter(function(family) {\n return appliesTo(family, kind);\n });\n }\n\n function utilityClass(family, tier, value) {\n if (family.className) { return family.className(tier.key, value); }\n\n return family.prefix + (tier.infix ? '-' + tier.infix : '') + '-' + value;\n }\n\n /** The value a node carries a class for at exactly this tier, or null. */\n function ownUtility(node, family, tier) {\n var classes = (node.getAttribute('class') || '').split(/\\s+/);\n\n for (var i = 0; i < family.values.length; i++) {\n if (classes.indexOf(utilityClass(family, tier, family.values[i])) !== -1) {\n return family.values[i];\n }\n }\n\n return null;\n }\n\n /**\n * The tier below this one that decides the value here, and what it\n * says, when this tier says nothing itself. Null when nothing below\n * says anything either.\n */\n function inheritedUtility(node, family, tier) {\n for (var i = BREAKPOINTS.indexOf(tier) - 1; i >= 0; i--) {\n var value = ownUtility(node, family, BREAKPOINTS[i]);\n if (value !== null) { return { tier: BREAKPOINTS[i], value: value }; }\n }\n\n return null;\n }\n\n /** What applies at a tier: its own class, or what it inherits. */\n function effectiveUtility(node, family, tier) {\n var own = ownUtility(node, family, tier);\n if (own !== null) { return own; }\n\n var inherited = inheritedUtility(node, family, tier);\n return inherited ? inherited.value : null;\n }\n\n /** Every tier the node carries a class of this family for. */\n function utilityTiers(node, family) {\n return BREAKPOINTS.map(function(tier) {\n return { tier: tier, value: ownUtility(node, family, tier) };\n }).filter(function(entry) { return entry.value !== null; });\n }\n\n function writeUtility(node, family, tier, value) {\n family.values.forEach(function(candidate) {\n dom.removeClass(node, utilityClass(family, tier, candidate));\n });\n\n if (value !== null) { dom.addClass(node, utilityClass(family, tier, value)); }\n dom.dropEmptyClass(node);\n }\n\n /**\n * What a view reads. A breakpoint reads what applies there. The all\n * view reads the class with no infix, since that is what it writes:\n * the one class that means \"the same at every size\".\n */\n function readUtility(node, family, view) {\n return view === ALL_VIEW\n ? ownUtility(node, family, BREAKPOINTS[0])\n : effectiveUtility(node, family, breakpoint(view));\n }\n\n /**\n * What writing `value` in a view comes to, or null when it changes\n * nothing. A breakpoint writes its own tier and nothing else. The all\n * view writes the class with no infix and clears the family from\n * every other tier, and says what it cleared: choosing one value for\n * every size is choosing it over what the sizes said.\n */\n function planUtility(node, family, view, value) {\n if (view !== ALL_VIEW) {\n var tier = breakpoint(view);\n if (ownUtility(node, family, tier) === value) { return null; }\n\n return { writes: [{ tier: tier, value: value }], cleared: [] };\n }\n\n var writes = [];\n var cleared = [];\n\n utilityTiers(node, family).forEach(function(entry) {\n if (entry.tier === BREAKPOINTS[0]) { return; }\n\n writes.push({ tier: entry.tier, value: null });\n cleared.push({ breakpoint: entry.tier.key, value: entry.value });\n });\n\n if (ownUtility(node, family, BREAKPOINTS[0]) !== value) {\n writes.unshift({ tier: BREAKPOINTS[0], value: value });\n }\n\n return writes.length ? { writes: writes, cleared: cleared } : null;\n }\n\n /** getUtility(node, family, view?): the value that applies, or null. */\n function getUtility(node, name, view) {\n node = nodeFrom(node);\n\n var family = familyNamed(name, 'getUtility');\n if (!family || !node) { return null; }\n\n var key = view === undefined ? curView : viewKey(view);\n if (key === null) {\n warn('getUtility(' + JSON.stringify(view) + '): no such layout mode');\n return null;\n }\n\n return readUtility(node, family, key);\n }\n\n /**\n * setUtility(node, family, value, view?): write a value through the\n * events. Null is \"inherit\". The last argument is a view key, or\n * { view, source } from a plugin that wants its tool named in the\n * payload. False when a handler canceled or nothing changed.\n */\n function setUtility(node, name, value, options) {\n options = typeof options == 'string' ? { view: options } : (options || {});\n node = nodeFrom(node);\n\n var family = familyNamed(name, 'setUtility');\n if (!family || !node) { return false; }\n\n var view = options.view === undefined ? curView : viewKey(options.view);\n if (view === null) {\n warn('setUtility(' + JSON.stringify(options.view) + '): no such layout mode');\n return false;\n }\n\n value = value === null || value === undefined || value === '' ? null : String(value);\n if (value !== null && family.values.indexOf(value) === -1) {\n warn('setUtility: ' + JSON.stringify(value) + ' is not a value of \"' + name +\n '\", which takes ' + JSON.stringify(family.values));\n return false;\n }\n\n var kind = kindOf(node);\n if (!appliesTo(family, kind)) {\n warn('setUtility: \"' + name + '\" does not apply to a ' + kind);\n return false;\n }\n\n // A family whose writes are some other operation - the column\n // width, which is a resize - does them its own way\n if (family.write) { return family.write(node, value, view, options.source || 'api'); }\n\n var plan = planUtility(node, family, view, value);\n if (!plan) { return false; }\n\n return operate(function() {\n var payload = payloadFor(kind, node, {\n family: name,\n breakpoint: view,\n tiers: plan.writes.map(function(write) { return write.tier.key; }),\n from: readUtility(node, family, view),\n to: value,\n cleared: plan.cleared,\n source: options.source || 'api',\n });\n\n if (!emit('before-utility', payload)) {\n // The panel already shows the value that was refused\n refreshUtilities(node);\n return false;\n }\n\n plan.writes.forEach(function(write) {\n writeUtility(node, family, write.tier, write.value);\n });\n refreshUtilities(node);\n emit('after-utility', payload);\n\n return true;\n });\n }\n\n /**\n * ge.bareStyle(node, family, property): what a css property comes to\n * on a node with none of the family's classes, at any breakpoint. The\n * answer a preview needs for \"no class applies here\" when that is not\n * a constant: text-align inherits from the parent, and the host's own\n * css may float an element. The browser is the only one who knows, so\n * the classes come off for the moment it takes to ask.\n */\n function bareStyle(node, name, property) {\n var family = familyNamed(name, 'bareStyle');\n node = nodeFrom(node);\n if (!family || !node) { return null; }\n\n var original = node.getAttribute('class');\n BREAKPOINTS.forEach(function(tier) { writeUtility(node, family, tier, null); });\n\n var value = getComputedStyle(node).getPropertyValue(property);\n\n if (original === null) { node.removeAttribute('class'); } else { node.setAttribute('class', original); }\n\n return value;\n }\n\n /** Bring a node's panel and preview up to date with its classes. */\n function refreshUtilities(node) {\n var details = detailsOf(node);\n\n if (details) {\n var classes = dom.one(details, '.ge-classes');\n if (classes) { classes.value = hostClasses(node).join(' '); }\n dom.children(details, '.ge-utilities').forEach(function(section) { renderUtilities(section); });\n }\n renderPluginFields(node);\n refreshPreviews(node);\n }\n\n /* Preview */\n\n function utilityNodes(scope) {\n return dom.selfAndAll(scope, UTILITY_NODES);\n }\n\n /**\n * Put what each node's utilities mean at the view being edited on the\n * node itself. Only nodes that carry a class of a family get anything,\n * and they get the family's answer for the view even when that is\n * \"nothing\": a wider tier's class is still live in a wide window, and\n * has to be overruled.\n *\n * The all view gets nothing. Its canvas is not narrowed, every tier is\n * live, and what Bootstrap shows is the truth.\n */\n function refreshPreviews(scope) {\n clearPreviews(scope);\n\n if (curView !== ALL_VIEW) { previewTier(scope, breakpoint(curView)); }\n\n markRowCols(scope);\n\n // Whatever a plugin marks the canvas with to show its utilities\n // goes stale at the same moments the preview does\n plugins('onRefresh', scope);\n }\n\n function previewTier(scope, tier) {\n utilityNodes(scope).forEach(function(node) {\n var kind = kindOf(node);\n var styles = {};\n\n familiesFor(kind).forEach(function(family) {\n if (!family.preview || !utilityTiers(node, family).length) { return; }\n\n Object.assign(styles, family.preview(effectiveUtility(node, family, tier), node, kind));\n });\n\n if (kind === 'column') { Object.assign(styles, rowColsPreview(node, tier)); }\n\n // A plugin whose families settle one property between them\n // previews the node as a whole\n Object.keys(UTILITIES).forEach(function(name) {\n var utility = UTILITIES[name];\n if (utility.preview) { Object.assign(styles, utility.preview(node, kind, tier.key)); }\n });\n\n if (Object.keys(styles).length) { applyPreview(node, styles); }\n });\n }\n\n /**\n * Set inline !important styles, which is the one thing that beats\n * Bootstrap's own !important, and remember what each property was so\n * it can be put back. The record is an attribute because a rich text\n * editor rebuilds the DOM of the area it edits, and the record has to\n * come back with the node.\n */\n function applyPreview(node, styles) {\n var style = node.style;\n var was = {};\n\n Object.keys(styles).forEach(function(property) {\n was[property] = [style.getPropertyValue(property), style.getPropertyPriority(property)];\n style.setProperty(property, String(styles[property]), 'important');\n });\n\n node.setAttribute(PREVIEW_ATTR, JSON.stringify(was));\n }\n\n function clearPreviews(scope) {\n dom.selfAndAll(scope, '[' + PREVIEW_ATTR + ']').forEach(function(node) {\n var style = node.style;\n var was = {};\n\n try { was = JSON.parse(node.getAttribute(PREVIEW_ATTR)) || {}; } catch (error) { /* a mangled record: drop it */ }\n\n Object.keys(was).forEach(function(property) {\n var before = was[property];\n\n if (before && before[0]) {\n style.setProperty(property, before[0], before[1]);\n } else {\n style.removeProperty(property);\n }\n });\n\n node.removeAttribute(PREVIEW_ATTR);\n dom.dropEmptyStyle(node);\n });\n }\n\n /* The host's own style, under the preview */\n\n /**\n * The node's style as the host wrote it: its declarations with every\n * property the preview set put back to what the preview recorded.\n * Held in a detached element's style, which parses and serializes it\n * the way the node's own would.\n */\n function hostDeclaration(node) {\n var scratch = document.createElement('div');\n var was = {};\n\n scratch.style.cssText = node.style.cssText;\n try { was = JSON.parse(node.getAttribute(PREVIEW_ATTR)) || {}; } catch (error) { /* no record */ }\n\n Object.keys(was).forEach(function(property) {\n var before = was[property];\n\n if (before && before[0]) {\n scratch.style.setProperty(property, before[0], before[1]);\n } else {\n scratch.style.removeProperty(property);\n }\n });\n\n return scratch.style;\n }\n\n /**\n * ge.hostStyle(node, property): { value, priority } of one property\n * of the host's style, never the preview's. With no property, the\n * host's whole style as css text.\n */\n function hostStyle(node, property) {\n var declaration = hostDeclaration(node);\n\n if (property === undefined) { return declaration.cssText; }\n\n return {\n value: declaration.getPropertyValue(property),\n priority: declaration.getPropertyPriority(property),\n };\n }\n\n /**\n * ge.setHostStyle(node, property, value, priority): write one property\n * of the host's style, or take it off with an empty value. The\n * preview comes off the node while it is written and goes back on\n * after, so what the preview put back on deinit is the host's new\n * value. False, and nothing written, when the browser refuses the\n * value. `priority` left out keeps the one the property had.\n */\n function setHostStyle(node, property, value, priority) {\n value = value === null || value === undefined ? '' : String(value).trim();\n\n if (priority === undefined) { priority = hostStyle(node, property).priority; }\n\n if (value !== '') {\n var check = document.createElement('div').style;\n check.setProperty(property, value, priority || '');\n if (check.getPropertyValue(property) === '') { return false; }\n }\n\n var previewed = node.hasAttribute(PREVIEW_ATTR);\n if (previewed) { clearPreviews(node); }\n\n if (value === '') {\n node.style.removeProperty(property);\n } else {\n node.style.setProperty(property, value, priority || '');\n }\n dom.dropEmptyStyle(node);\n\n if (previewed) { refreshPreviews(node); }\n\n return true;\n }\n\n /* The panel */\n\n /**\n * The Responsive section of a node's settings panel: one field per\n * family that applies to the node, reading and writing the view being\n * edited, and whatever fields a plugin builds itself. Folded until the\n * user unfolds one, and then unfolded on every node, since whoever\n * wanted it on one wants it on the next.\n */\n function createUtilitiesSection(node) {\n var kind = kindOf(node);\n var fields = familiesFor(kind)\n .filter(function(family) { return family.panel !== false; })\n .map(function(family) { return createField(node, family); });\n\n Object.keys(UTILITIES).forEach(function(name) {\n var utility = UTILITIES[name];\n var own = utility.panel ? utility.panel(node, kind) : null;\n if (own) { fields.push(own); }\n });\n\n if (!fields.length) { return null; }\n\n var section = dom.toggleClass(dom.element('div', { 'class': 'ge-utilities' }), 'ge-open', utilitiesOpen);\n sectionNodes.set(section, node);\n\n var toggle = section.appendChild(dom.element('a', { 'class': 'ge-utilities-toggle' }));\n toggle.addEventListener('click', function() {\n utilitiesOpen = !dom.hasClass(section, 'ge-open');\n settingsScope().forEach(function(scope) {\n dom.all(scope, '.ge-utilities').forEach(function(each) {\n dom.toggleClass(each, 'ge-open', utilitiesOpen);\n });\n });\n });\n\n var body = section.appendChild(dom.element('div', { 'class': 'ge-utilities-body' }));\n fields.forEach(function(field) { body.appendChild(field); });\n\n renderUtilities(section);\n\n return section;\n }\n\n /**\n * One family's field: its label, a select that writes through\n * setUtility, and a note. Filled by renderField, again whenever the\n * view or the node's classes change.\n */\n function createField(node, family) {\n var field = dom.element('label', { 'class': 'ge-utility', 'data-ge-family': family.name });\n\n field.appendChild(dom.element('span', { 'class': 'ge-utility-label' },\n family.labelKey ? t(family.labelKey) : family.name));\n\n var select = field.appendChild(dom.element('select', { 'class': 'form-select form-select-sm' }));\n select.addEventListener('change', function() {\n setUtility(node, family.name, this.value, { source: 'panel' });\n });\n\n field.appendChild(dom.element('small', { 'class': 'ge-utility-note' }));\n\n return field;\n }\n\n /** ge.utilityField(node, family): a field a plugin places in a panel of its own. */\n function utilityField(node, name) {\n var family = familyNamed(name, 'utilityField');\n if (!family) { return null; }\n\n var field = createField(node, family);\n renderField(field, node);\n pluginFields.set(field, node);\n\n return field;\n }\n\n /**\n * The fields a plugin made, wherever it put them: a Responsive\n * section renders its own, and these are the rest - in a plugin's\n * section of the panel, or in the dialog. Each one's node's, or\n * every node's; a field no longer on the page is forgotten.\n */\n var pluginFields = new Map(); // field -> the node it edits\n\n function renderPluginFields(node) {\n pluginFields.forEach(function(fieldNode, field) {\n if (!field.isConnected) {\n pluginFields.delete(field);\n return;\n }\n if (node && fieldNode !== node) { return; }\n if (dom.closest(field, '.ge-utilities')) { return; }\n\n renderField(field, fieldNode);\n });\n }\n\n /** Fill a section's fields, the families' and the plugins' own, for the view being edited. */\n function renderUtilities(section) {\n var node = sectionNodes.get(section);\n\n dom.children(section, '.ge-utilities-toggle').forEach(function(toggle) {\n toggle.textContent = t('utility.section', { view: t(labelKeyFor(curView)) });\n });\n\n dom.all(section, '.ge-utility').forEach(function(field) { renderField(field, node); });\n }\n\n function renderField(field, node) {\n var family = FAMILIES[field.getAttribute('data-ge-family')].family;\n var select = dom.child(field, 'select');\n var choices = family.choices ? family.choices(node, kindOf(node)) : family.values;\n var own, blank, note = '';\n\n select.innerHTML = '';\n\n if (curView === ALL_VIEW) {\n own = ownUtility(node, family, BREAKPOINTS[0]);\n blank = t('utility.default');\n\n var varies = utilityTiers(node, family).filter(function(entry) {\n return entry.tier !== BREAKPOINTS[0];\n });\n if (varies.length) {\n note = t('utility.varies', {\n breakpoints: varies.map(function(entry) { return entry.tier.key; }).join(', '),\n });\n }\n } else {\n var tier = breakpoint(curView);\n var inherited = inheritedUtility(node, family, tier);\n\n own = ownUtility(node, family, tier);\n blank = inherited\n ? t('utility.inherit', { value: labelOf(family, inherited.value), breakpoint: inherited.tier.key })\n : t('utility.default');\n\n // What the empty choice means is sometimes not the family's\n // own business: a column's width can come from its row\n var custom = family.blank ? family.blank(node, curView) : null;\n if (custom && own === null) { blank = custom; }\n }\n\n // A value the markup carries is shown even when the family\n // would not offer it here, rather than shown as something else\n if (own !== null && choices.indexOf(own) === -1) { choices = choices.concat([own]); }\n\n select.appendChild(dom.element('option', { value: '' }, blank));\n choices.forEach(function(value) {\n select.appendChild(dom.element('option', { value: value }, labelOf(family, value)));\n });\n\n select.value = own === null ? '' : own;\n\n var noteNode = dom.child(field, '.ge-utility-note');\n noteNode.textContent = note;\n dom.toggle(noteNode, note !== '');\n }\n\n function labelOf(family, value) {\n return family.label ? family.label(value) : value;\n }\n\n /* --------------------------------------------------------------\n * Containers: tabs, accordions, popups, carousels and cards.\n *\n * A container holds panes, and a pane is an ordinary canvas region -\n * rows, columns, content areas and elements nest inside one exactly\n * as they do at the top level, because init() walks the whole canvas\n * and does not care how deep it is.\n *\n * What a container is, is said by data-ge-container. The ge-* classes\n * are editing furniture and come off with everything else, so a host\n * restyling the markup cannot break detection and getHtml stays clean.\n * -------------------------------------------------------------- */\n\n var CONTAINERS = {}; // The container plugins in use, by the type each builds\n var FEATURES = {}; // The feature plugins in use, by name\n var UTILITIES = {}; // The utility plugins in use, by name\n var featureMethods = {}; // The methods those features contribute\n var containerCounter = 0;\n\n /**\n * Ids go into the markup rather than into memory: Bootstrap's toggles\n * are written in terms of them, and the markup has to survive getHtml\n * with those toggles still pointing at the right panes.\n */\n function containerId(type) {\n containerCounter++;\n\n return 'ge-' + type + '-' + containerCounter + '-' +\n Math.random().toString(36).slice(2, 6);\n }\n\n /** A pane's starting content: one full width column, ready to edit. */\n function defaultRegion() {\n var row = createRow();\n row.appendChild(createColumn(MAX_COL_SIZE));\n return row;\n }\n\n function containerTypeOf(container) {\n return container ? container.getAttribute('data-ge-container') : null;\n }\n\n function markContainers() {\n dom.all(canvas, '[data-ge-container]').forEach(function(container) {\n var type = containerTypeOf(container);\n var definition = CONTAINERS[type];\n\n if (!definition) {\n warnOnceHere('container:' + type, 'unknown container type \"' + type + '\"');\n return;\n }\n\n dom.addClass(container, 'ge-container ge-container-' + type);\n definition.mark(container);\n\n if (!dom.child(container, '.ge-tools-drawer')) {\n createContainerControls(container, type, definition);\n }\n });\n }\n\n function unmarkContainers() {\n dom.all(canvas, '[data-ge-container]').forEach(function(container) {\n var definition = CONTAINERS[containerTypeOf(container)];\n\n if (definition) { definition.unmark(container); }\n\n unmarkContainerClasses(container);\n });\n }\n\n function unmarkContainerClasses(container) {\n dom.removeClass(container, 'ge-container ge-container-' + containerTypeOf(container));\n dom.dropEmptyClass(container);\n }\n\n /** A new drawer as the first child of `node`. */\n function prependDrawer(node, className) {\n var drawer = dom.element('div', { 'class': className });\n node.insertBefore(drawer, node.firstChild);\n return drawer;\n }\n\n /** The host's own tools, from a *_tools setting, in a drawer. */\n function hostTools(drawer, tools) {\n (tools || []).forEach(function(hostTool) {\n createTool(drawer, hostTool.title || '', hostTool.className || '',\n hostTool.iconClass || 'bi bi-wrench', hostTool.on);\n });\n }\n\n function createContainerControls(container, type, definition) {\n var drawer = prependDrawer(container, 'ge-tools-drawer ge-container-drawer');\n\n createMoveTool(drawer);\n addSettingsTool(drawer, container, settings.container_classes);\n\n hostTools(drawer, settings.container_tools);\n\n if (definition.tools) { definition.tools(drawer, container); }\n\n createTool(drawer, t('tool.delete_container'), 'ge-delete-container', 'bi bi-trash', function() {\n deleteNode(type, container, t('confirm.delete_container'), function(removed) {\n dom.slideUp(container, removed);\n });\n });\n\n // Delete then add, the order rows and columns have\n if (definition.addPane) {\n createTool(drawer, t(definition.addPaneKey), 'ge-add-pane', 'bi bi-plus-circle', function() {\n var pane = definition.addPane(container, {});\n if (!pane) { return; }\n\n addNode(definition.paneKind, pane, function() {}, {\n parent: container,\n source: 'tool',\n container: container,\n });\n });\n }\n }\n\n /**\n * A pane drawer: small, inline, and made the same way for every\n * container type so a tab and an accordion item behave alike.\n */\n function createPaneControls(pane, kind, tools, confirmText, remove) {\n var drawer = prependDrawer(pane, 'ge-tools-drawer ge-pane-drawer');\n\n createMoveTool(drawer);\n addSettingsTool(drawer, pane, settings.pane_classes);\n\n hostTools(drawer, tools);\n\n createTool(drawer, t('tool.delete_pane'), 'ge-delete-pane', 'bi bi-trash', function() {\n deleteNode(kind, pane, confirmText, function(removed) {\n remove(removed);\n });\n });\n\n return drawer;\n }\n\n /**\n * Take a Bootstrap toggle away from a node, and give it back later.\n *\n * Bootstrap binds its data-api handlers on the document in the\n * capture phase, so a listener on the node cannot stop one: the\n * document sees the click first. What does work is leaving nothing\n * for its selector to match, so the attribute is moved aside while\n * the editor needs the control not to react, and moved back on the\n * way out.\n *\n * The attributes are the ones Bootstrap's data api acts on: the tabs',\n * accordions' and popups' toggles and dismisses, and a carousel's\n * slide controls and autoplay.\n */\n var TOGGLE_ATTRIBUTES = ['toggle', 'dismiss', 'slide', 'slide-to', 'ride'];\n\n function suspendToggles(scope) {\n if (!scope) { return; }\n\n dom.selfAndAll(scope, TOGGLE_ATTRIBUTES.map(function(name) { return '[data-bs-' + name + ']'; }).join(', '))\n .forEach(function(node) {\n TOGGLE_ATTRIBUTES.forEach(function(name) {\n var value = node.getAttribute('data-bs-' + name);\n if (value === null) { return; }\n\n node.setAttribute('data-ge-bs-' + name, value);\n node.removeAttribute('data-bs-' + name);\n });\n });\n }\n\n function resumeToggles(scope) {\n if (!scope) { return; }\n\n dom.selfAndAll(scope, TOGGLE_ATTRIBUTES.map(function(name) { return '[data-ge-bs-' + name + ']'; }).join(', '))\n .forEach(function(node) {\n TOGGLE_ATTRIBUTES.forEach(function(name) {\n var value = node.getAttribute('data-ge-bs-' + name);\n if (value === null) { return; }\n\n node.setAttribute('data-bs-' + name, value);\n node.removeAttribute('data-ge-bs-' + name);\n });\n });\n }\n\n /**\n * Rename a label in place. The label sits inside the button Bootstrap\n * toggles from, so the toggle is suspended while the label is being\n * edited: typing in a tab's name must not switch tabs.\n */\n function makeLabelEditable(label) {\n if (editableLabels.has(label)) { return; }\n\n var toggle = dom.closest(label, '[data-bs-toggle], [data-ge-bs-toggle]');\n\n editableLabels.add(label);\n label.setAttribute('title', t('tool.rename'));\n label.addEventListener('dblclick', function(e) {\n e.preventDefault();\n e.stopPropagation();\n\n suspendToggles(toggle);\n label.setAttribute('contenteditable', 'true');\n label.focus();\n window.getSelection().selectAllChildren(label);\n });\n label.addEventListener('keydown', function(e) {\n if (label.getAttribute('contenteditable') !== 'true') { return; }\n\n if (e.key === 'Enter') {\n e.preventDefault();\n label.blur();\n }\n });\n label.addEventListener('blur', function() {\n label.removeAttribute('contenteditable');\n resumeToggles(toggle);\n });\n }\n\n /** The label inside a pane's button, wrapped so it can be edited alone. */\n function labelIn(button) {\n var label = dom.child(button, '.ge-pane-label');\n\n if (!label) {\n label = dom.element('span', { 'class': 'ge-pane-label' }, button.textContent.trim());\n button.innerHTML = '';\n button.appendChild(label);\n }\n\n return label;\n }\n\n function unwrapLabels(scope) {\n dom.all(scope, '.ge-pane-label').forEach(function(label) {\n editableLabels.delete(label);\n dom.unwrap(label);\n });\n }\n\n /**\n * Add a column of `size` to a row, through the add events.\n */\n function addColumnTo(row, size) {\n var column = createColumn(size);\n\n return addNode('column', column, function() {\n row.appendChild(column);\n }, { parent: row, source: 'tool' });\n }\n\n /**\n * Holding the add column tool offers the sizes instead of taking the\n * default one.\n *\n * Held rather than hovered alone, because a hover is a gesture a touch\n * screen does not have, and the tooltip says so: a gesture nobody can\n * see is a gesture nobody finds.\n */\n function attachSizePicker(tool, row) {\n if (!settings.add_column.picker || !tool) { return; }\n\n attachPicker(tool, function() { openSizePicker(tool, row); });\n }\n\n /**\n * Hold a tool - or rest the pointer on it - and `open` offers a\n * choice under it. The add text tool offers its editors the same way.\n */\n function attachPicker(tool, open) {\n var timer = null;\n\n var cancel = function() {\n window.clearTimeout(timer);\n timer = null;\n };\n\n dom.on(tool, 'mouseenter mousedown', function() {\n if (timer || sizePicker) { return; }\n\n timer = window.setTimeout(function() {\n timer = null;\n open();\n }, settings.add_column.delay);\n });\n\n dom.on(tool, 'mouseleave mouseup', cancel);\n }\n\n /**\n * The sizes a column may be given, as a strip under the tool. Sizes\n * that do not fit what is left of the row are marked, not withheld:\n * a row is allowed to wrap, and that is the host's page to lay out.\n */\n function openSizePicker(tool, row) {\n closeSizePicker();\n\n var room = spare(row, leadingTier());\n\n // The drawer it hangs off is raised while it is open: drawers sit\n // below the resize handles, so without this the drawer of the\n // column below takes the clicks meant for the picker\n var drawer = dom.closest(tool, '.ge-tools-drawer');\n if (drawer) { dom.addClass(drawer, 'ge-picker-open'); }\n\n sizePicker = tool.appendChild(dom.element('div', { 'class': 'ge-size-picker' }));\n\n settings.valid_col_sizes.forEach(function(size) {\n var choice = dom.element('a', {\n 'class': 'ge-size',\n 'data-ge-size': size,\n title: sizeTitle(size),\n }, isUnits(size) ? size : sizeClass(BREAKPOINTS[0], size));\n\n dom.toggleClass(choice, 'ge-size-tight', isUnits(size) && size > room);\n dom.toggleClass(choice, 'ge-size-flex', !isUnits(size));\n choice.addEventListener('click', function(e) {\n e.preventDefault();\n e.stopPropagation();\n\n closeSizePicker();\n addColumnTo(row, size);\n });\n sizePicker.appendChild(choice);\n });\n\n // Anywhere else, and the question is withdrawn\n withdrawOnLeave(tool);\n }\n\n function sizeTitle(size) {\n if (size === 'equal') { return t('tool.column_equal'); }\n if (size === 'auto') { return t('tool.column_auto'); }\n\n return t('tool.column_size', { size: size });\n }\n\n /** True when there was one to close, which is also a click's answer. */\n function closeSizePicker() {\n if (!sizePicker) { return false; }\n\n var drawer = dom.closest(sizePicker, '.ge-tools-drawer');\n if (drawer) { dom.removeClass(drawer, 'ge-picker-open'); }\n sizePicker.remove();\n sizePicker = null;\n\n return true;\n }\n\n function createRowControls() {\n dom.all(canvas, '.row').forEach(function(row) {\n if (dom.child(row, '.ge-tools-drawer')) { return; }\n\n var drawer = prependDrawer(row, 'ge-tools-drawer');\n createMoveTool(drawer);\n addSettingsTool(drawer, row, settings.row_classes);\n\n hostTools(drawer, settings.row_tools);\n createTool(drawer, t('tool.delete_row'), 'ge-delete-row', 'bi bi-trash', function() {\n deleteNode('row', row, t('confirm.delete_row'), function(removed) {\n dom.slideUp(row, removed);\n });\n });\n createTool(drawer, t('tool.add_column'), 'ge-add-column', 'bi bi-plus-circle', function() {\n if (closeSizePicker()) { return; } // The picker was open: that was the answer\n\n // In a row with row-cols the new column takes its share\n addColumnTo(row, rowColsSource(row, leadingTier()) ? null : settings.add_column.size);\n });\n\n attachSizePicker(dom.child(drawer, '.ge-add-column'), row);\n\n });\n }\n\n function createColControls() {\n dom.all(canvas, '.column').forEach(function(col) {\n if (dom.child(col, '.ge-tools-drawer')) { return; }\n\n var drawer = prependDrawer(col, 'ge-tools-drawer');\n\n createMoveTool(drawer);\n\n if (settings.resize.tools !== false) {\n createTool(drawer, t('tool.column_narrower'), 'ge-decrease-col-width', 'bi bi-dash-lg', function(e) {\n resizeColumn(col, e.shiftKey\n ? smallest(settings.valid_col_sizes)\n : stepThrough(settings.valid_col_sizes.filter(isUnits), currentUnits(col), -1),\n 'tool');\n });\n\n createTool(drawer, t('tool.column_wider'), 'ge-increase-col-width', 'bi bi-plus-lg', function(e) {\n resizeColumn(col, e.shiftKey\n ? widestFor(col)\n : stepThrough(settings.valid_col_sizes.filter(isUnits), currentUnits(col), 1),\n 'tool');\n });\n }\n\n if (settings.indent.tools !== false) {\n createTool(drawer, t('tool.indent_decrease'), 'ge-decrease-col-offset', 'bi bi-text-indent-right', function(e) {\n indentColumn(col, e.shiftKey\n ? smallest(settings.valid_col_offsets)\n : stepThrough(settings.valid_col_offsets, currentOffset(col), -1),\n 'tool');\n });\n\n createTool(drawer, t('tool.indent_increase'), 'ge-increase-col-offset', 'bi bi-text-indent-left', function(e) {\n indentColumn(col, e.shiftKey ? deepestFor(col) : stepThrough(settings.valid_col_offsets, currentOffset(col), 1), 'tool');\n });\n }\n\n addSettingsTool(drawer, col, settings.col_classes);\n\n hostTools(drawer, settings.col_tools);\n\n createTool(drawer, t('tool.delete_column'), 'ge-delete-column', 'bi bi-trash', function() {\n deleteNode('column', col, t('confirm.delete_column'), function(removed) {\n dom.shrinkAway(col, 400, removed, true);\n });\n });\n\n createTool(drawer, t('tool.add_row'), 'ge-add-row', 'bi bi-plus-circle', function() {\n // An empty row: the columns in it are the next decision,\n // and its drawer's add column tool is where that is made\n var row = createRow();\n\n addNode('row', row, function() {\n col.appendChild(row);\n }, { parent: col, source: 'tool' });\n });\n\n });\n }\n\n /**\n * The tier the tools read when they need one number.\n *\n * In a per-breakpoint view that is the tier being edited. In the all\n * view it is the widest tier, because the canvas is not constrained\n * there and the widest tier is what the user is looking at: clicking\n * \"narrower\" on a column authored as col-lg-6 should take it to 5,\n * not to 11 because no base class was ever written. What the all view\n * writes is the base class all the same.\n */\n function leadingTier() {\n return curView === ALL_VIEW ? BREAKPOINTS[BREAKPOINTS.length - 1] : breakpoint(curView);\n }\n\n /** The size that applies in the view: units, `equal` or `auto`. */\n function currentSize(col) {\n var tier = leadingTier();\n\n // Sized by its row: it has no size of its own to report\n if (rowColsWinner(col, tier)) { return null; }\n\n var size = getEffectiveSize(col, tier);\n return size === null ? MAX_COL_SIZE : size;\n }\n\n /**\n * The size in units, which is what the tools step through. An equal\n * or auto column has no number, so it is measured: the width it has\n * on the canvas, in twelfths of its row.\n */\n function currentUnits(col) {\n var size = currentSize(col);\n if (isUnits(size)) { return size; }\n\n var units = Math.round(dom.outerWidth(col) / rowContentWidth(col.parentElement) * MAX_COL_SIZE);\n return Math.min(Math.max(units, 1), MAX_COL_SIZE);\n }\n\n function rowContentWidth(row) {\n var style = window.getComputedStyle(row);\n\n return row.clientWidth - parseFloat(style.paddingLeft) - parseFloat(style.paddingRight);\n }\n\n function currentOffset(col) {\n return getEffectiveOffset(col, leadingTier()) || 0;\n }\n\n /** The next value a tool moves to, one step along the allowed list. */\n function stepThrough(values, from, direction) {\n var index = values.indexOf(from);\n\n if (index === -1) {\n // A value the host did not allow: step to the nearest one it did\n return values.reduce(function(best, value) {\n return Math.abs(value - from) < Math.abs(best - from) ? value : best;\n }, values[0]);\n }\n\n return values[Math.min(Math.max(index + direction, 0), values.length - 1)];\n }\n\n function smallest(values) {\n return values.filter(isUnits).reduce(function(a, b) { return Math.min(a, b); }, MAX_COL_SIZE);\n }\n\n function largest(values) {\n return values.filter(isUnits).reduce(function(a, b) { return Math.max(a, b); }, 0);\n }\n\n /**\n * The widest this column can be: everything the row has left, minus\n * its own indent. What \"hold shift for max\" means.\n */\n function widestFor(col) {\n var room = spare(col.parentElement, leadingTier(), col) - currentOffset(col);\n\n return Math.min(largest(settings.valid_col_sizes), Math.max(room, 1));\n }\n\n /**\n * The deepest this column can be indented and still have a unit of\n * itself left inside the row.\n */\n function deepestFor(col) {\n var room = spare(col.parentElement, leadingTier(), col) - currentUnits(col);\n\n return Math.min(largest(settings.valid_col_offsets), Math.max(room, 0));\n }\n\n /**\n * The move tool, unless the whole drawer is the handle - in which case\n * a tool that only says \"drag from here\" is one tool too many.\n */\n function createMoveTool(drawer) {\n if (settings.drag_handle === 'drawer') { return null; }\n\n return createTool(drawer, t('tool.move'), 'ge-move', 'bi bi-arrows-move');\n }\n\n /**\n * The drawers that span their node - a row's, a column's, a\n * container's, an element's, a section's - keep their tools to one\n * line. The tools that don't fit are hidden from the end, and a more\n * tool at the drawer's end unfolds it to show them all, wrapping as\n * it would otherwise. They stay where they are, so whatever finds a\n * tool in its drawer, or hangs a picker off it, still does.\n *\n * A text's drawer sits over the text, as wide as its tools, and a\n * pane's sits by its label: neither is one of them.\n */\n var FITTED_DRAWERS = '.ge-tools-drawer:not(.ge-text-drawer):not(.ge-pane-drawer):not(.ge-code-inline)';\n\n /**\n * Fit every drawer as it comes onto the canvas, and again when it\n * changes width or a tool is added to it, shown or hidden. Plugins\n * add tools at their own moments, so this watches rather than\n * waiting to be told.\n */\n function watchDrawers() {\n if (settings.drawer_overflow === 'wrap' || !window.ResizeObserver || !window.MutationObserver) { return; }\n\n var due = new Set();\n var frame = null;\n\n // Once a frame, after the layout: moving tools in the observers'\n // callbacks would resize what they are watching\n function schedule(drawer) {\n due.add(drawer);\n if (frame === null) { frame = window.requestAnimationFrame(flush); }\n }\n\n function flush() {\n frame = null;\n var drawers = Array.from(due);\n due.clear();\n drawers.forEach(function(drawer) {\n if (!drawer.isConnected) {\n drawerResizes.unobserve(drawer);\n return;\n }\n fitDrawer(drawer);\n });\n }\n\n var drawerResizes = new window.ResizeObserver(function(entries) {\n entries.forEach(function(entry) { schedule(entry.target); });\n });\n\n var mutations = new window.MutationObserver(function(records) {\n records.forEach(function(record) {\n var target = record.target;\n\n // A tool shown or hidden\n if (record.type === 'attributes') {\n var parent = target.parentNode;\n if (parent && parent.nodeType === 1 && parent.matches(FITTED_DRAWERS)) { schedule(parent); }\n return;\n }\n\n // A tool added\n if (target.nodeType === 1 && target.matches(FITTED_DRAWERS)) {\n schedule(target);\n return;\n }\n\n record.addedNodes.forEach(function(node) {\n if (node.nodeType !== 1) { return; }\n dom.selfAndAll(node, FITTED_DRAWERS).forEach(function(drawer) {\n dom.addClass(drawer, 'ge-drawer-fit');\n drawerResizes.observe(drawer);\n schedule(drawer);\n });\n });\n });\n });\n mutations.observe(canvas, { childList: true, subtree: true, attributes: true, attributeFilter: ['style'] });\n\n lifetime.signal.addEventListener('abort', function() {\n mutations.disconnect();\n drawerResizes.disconnect();\n if (frame !== null) { window.cancelAnimationFrame(frame); }\n });\n }\n\n /** Hide the tools that don't fit on the drawer's line, from the end, behind its more tool. */\n function fitDrawer(drawer) {\n var tools = dom.children(drawer, 'a').filter(function(tool) { return !dom.hasClass(tool, 'ge-drawer-more'); });\n var expanded = dom.hasClass(drawer, 'ge-drawer-expanded');\n\n // Measured on one line, with every tool back on it\n dom.removeClass(drawer, 'ge-drawer-overflow ge-drawer-expanded');\n tools.forEach(function(tool) { dom.removeClass(tool, 'ge-tool-overflow'); });\n\n if (!drawerOverflows(drawer, tools)) { return; }\n\n dom.addClass(drawer, 'ge-drawer-overflow');\n if (!dom.child(drawer, '.ge-drawer-more')) {\n createTool(drawer, t('tool.more'), 'ge-drawer-more', 'bi bi-three-dots', function() {\n dom.toggleClass(drawer, 'ge-drawer-expanded');\n });\n }\n\n for (var i = tools.length - 1; i >= 0 && drawerOverflows(drawer, tools); i--) {\n dom.addClass(tools[i], 'ge-tool-overflow');\n }\n\n dom.toggleClass(drawer, 'ge-drawer-expanded', expanded);\n }\n\n function drawerOverflows(drawer, tools) {\n var style = window.getComputedStyle(drawer);\n var limit = drawer.getBoundingClientRect().right -\n parseFloat(style.borderRightWidth) - parseFloat(style.paddingRight);\n\n return tools.some(function(tool) {\n var rects = tool.getClientRects();\n return rects.length > 0 && rects[0].right > limit + 0.5;\n });\n }\n\n /**\n * A tool in a drawer: a link with an icon, and what it does. The\n * handlers are a click handler, or { eventName: handler }; each gets\n * the DOM event, with `this` the tool. Hands back the tool.\n */\n function createTool(drawer, title, className, iconClass, eventHandlers) {\n // Through setAttribute rather than spliced into markup: a title is\n // text, and a quote in it - a type name, a host's own title -\n // would end the attribute early\n var tool = dom.element('a', { title: title, 'class': className });\n tool.appendChild(dom.element('i', { 'class': iconClass }));\n drawer.appendChild(tool);\n\n if (typeof eventHandlers == 'function') {\n tool.addEventListener('click', eventHandlers);\n }\n if (eventHandlers && typeof eventHandlers == 'object') {\n Object.keys(eventHandlers).forEach(function(name) {\n dom.on(tool, name, eventHandlers[name]);\n });\n }\n\n return tool;\n }\n\n /**\n * The classes on a node that are the host's own, rather than the ones\n * the grid and the editor put there. What the settings panel shows,\n * and the only ones it is allowed to take away.\n */\n function hostClasses(node) {\n return (node.getAttribute('class') || '').split(/\\s+/).filter(function(name) {\n return name !== '' && !isEditorClass(name);\n });\n }\n\n function isEditorClass(name) {\n if (name === 'row' || name === 'column') { return true; }\n if (/^(ge-|ui-)/.test(name)) { return true; }\n if (/^col(-(sm|md|lg|xl|xxl))?(-auto)?$/.test(name)) { return true; }\n\n return BREAKPOINTS.some(function(tier) {\n return new RegExp('^(' + tier.colPrefix + '|' + tier.offsetPrefix + ')\\\\d+$').test(name);\n });\n }\n\n function setHostClasses(node, value) {\n hostClasses(node).forEach(function(name) { dom.removeClass(node, name); });\n\n value.split(/\\s+/).forEach(function(name) {\n if (name !== '') { dom.addClass(node, name); }\n });\n\n dom.dropEmptyClass(node);\n }\n\n /**\n * The gear and the panel it opens: the node's id, its css classes, and\n * whatever preset toggles the host configured for that kind of node.\n */\n function addSettingsTool(drawer, node, presets) {\n var details = createDetails(node, presets || []);\n detailsFor.set(node, details);\n\n // The sidebar shows the panel of the node that is selected, so\n // there is no gear to open it with\n if (panelMode() !== 'sidebar') {\n createTool(drawer, t('tool.settings'), 'ge-settings', 'bi bi-gear-fill', function() {\n toggleSettings(node, details, this);\n });\n }\n\n // Beside the gear, because every node that has one is a node a\n // utility may apply to, whichever plugin built its drawer. A\n // feature plugin's tools go there too, for the same reason: the\n // gear is the one tool every drawer has.\n var kind = kindOf(node);\n Object.keys(UTILITIES).forEach(function(name) {\n if (UTILITIES[name].drawerTools) { UTILITIES[name].drawerTools(drawer, node, kind); }\n });\n Object.keys(FEATURES).forEach(function(name) {\n if (FEATURES[name].drawerTools) { FEATURES[name].drawerTools(drawer, node, kind); }\n });\n\n return drawer.appendChild(details);\n }\n\n function createDetails(container, cssClasses) {\n var detailsDiv = dom.element('div', { 'class': 'ge-details' });\n detailsDiv.appendChild(sectionTitle(t('panel.section_general')));\n var general = detailsDiv.appendChild(dom.element('div', { 'class': 'ge-details-general' }));\n var field = function(label) {\n var holder = dom.element('label', { 'class': 'ge-field' });\n holder.appendChild(dom.element('span', { 'class': 'ge-field-label' }, label));\n return general.appendChild(holder);\n };\n\n var id = dom.element('input', {\n 'class': 'ge-id form-control form-control-sm',\n placeholder: t('tool.id_placeholder'),\n title: t('tool.id_title'),\n });\n id.value = container.getAttribute('id') || '';\n field(t('panel.id')).appendChild(id);\n id.addEventListener('change', function() {\n // An empty field means no id, not an empty one\n if (this.value === '') {\n container.removeAttribute('id');\n } else {\n container.setAttribute('id', this.value);\n }\n });\n\n var classes = dom.element('input', {\n 'class': 'ge-classes form-control form-control-sm',\n placeholder: t('tool.classes_placeholder'),\n title: t('tool.classes_title'),\n });\n classes.value = hostClasses(container).join(' ');\n field(t('panel.classes')).appendChild(classes);\n classes.addEventListener('change', function() {\n setHostClasses(container, this.value);\n refreshUtilities(container);\n });\n\n // Bootstrap's outline buttons, filled while their class is on\n var classGroup = general.appendChild(dom.element('div', { 'class': 'btn-group btn-group-sm ge-presets', role: 'group' }));\n cssClasses.forEach(function(rowClass) {\n var on = dom.hasClass(container, rowClass.cssClass);\n var btn = dom.element('a', {\n role: 'button',\n 'class': 'btn btn-sm btn-outline-secondary',\n title: rowClass.title ? rowClass.title : t('tool.toggle_class', { label: rowClass.label }),\n 'aria-pressed': on ? 'true' : 'false',\n });\n\n // A preset's label is the host's markup\n btn.innerHTML = rowClass.label;\n dom.toggleClass(btn, 'active', on);\n btn.addEventListener('click', function() {\n dom.toggleClass(btn, 'active');\n btn.setAttribute('aria-pressed', dom.hasClass(btn, 'active') ? 'true' : 'false');\n dom.toggleClass(container, rowClass.cssClass, dom.hasClass(btn, 'active'));\n refreshUtilities(container);\n });\n classGroup.appendChild(btn);\n });\n\n pluginSections(container).forEach(function(section) { detailsDiv.appendChild(section); });\n\n var utilities = createUtilitiesSection(container);\n if (utilities) { detailsDiv.appendChild(utilities); }\n\n return detailsDiv;\n }\n\n /** The heading of one of a panel's sections. */\n function sectionTitle(text) {\n return dom.element('h6', { 'class': 'ge-section-title' }, text);\n }\n\n /**\n * What plugins add to a node's panel, between its general fields and\n * the Responsive section: each plugin's panelSection(node, kind), in\n * the order they were registered. Where the panel has room - the\n * offcanvas, the modal - the section is in it. A popover or a panel\n * inline in the drawer gets a button instead, and the section opens\n * in the dialog.\n */\n function pluginSections(node) {\n var kind = kindOf(node);\n var mode = panelMode();\n var sections = [];\n\n [CONTAINERS, FEATURES, UTILITIES].forEach(function(registry) {\n Object.keys(registry).forEach(function(name) {\n var plugin = registry[name];\n var section = plugin.panelSection ? plugin.panelSection(node, kind) : null;\n if (!section || !section.body) { return; }\n\n var holder = dom.element('div', { 'class': 'ge-panel-section', 'data-ge-plugin': name });\n\n if (mode === 'offcanvas' || mode === 'modal' || mode === 'sidebar') {\n holder.appendChild(sectionTitle(t(section.labelKey)));\n holder.appendChild(section.body);\n } else {\n var label = t(section.labelKey);\n var open = holder.appendChild(dom.element('button', {\n type: 'button',\n 'class': 'btn btn-sm btn-outline-secondary ge-panel-section-open',\n }, label));\n\n dom.hide(section.body);\n holder.appendChild(section.body);\n open.addEventListener('click', function() {\n openDialog(section.titleKey ? t(section.titleKey, { kind: kindLabel(node) }) : label,\n section.body, open);\n });\n }\n\n sections.push(holder);\n });\n });\n\n return sections;\n }\n\n /* --------------------------------------------------------------\n * Where a node's settings open.\n *\n * Each node's panel - createDetails' fields, and what plugins add to\n * them - is built into its drawer, as ever. settings_panel says where\n * it shows: 'inline' unfolds it in the drawer; 'offcanvas', 'popover'\n * and 'modal' move it into one of Bootstrap's, outside the canvas,\n * while it is open, and back into its drawer when it closes, so\n * everything that finds a panel through its node keeps working.\n *\n * Bootstrap's markup and styles, but the editor's own opening and\n * placing: a page may load Bootstrap's javascript without Popper, or\n * not at all. The modal is Bootstrap's own when Bootstrap is there.\n * -------------------------------------------------------------- */\n\n var PANEL_MODES = ['offcanvas', 'popover', 'modal', 'inline', 'sidebar'];\n var settingsPanels = {}; // One of each, built on first use, outside the canvas\n var openSettingsState = null; // What is open: { mode, node, details, home, next, gear }\n var modalState = new WeakMap(); // modal panel -> { watched, wanted, busy, backdrop, dismissed }\n\n function panelMode() {\n if (PANEL_MODES.indexOf(settings.settings_panel) !== -1) { return settings.settings_panel; }\n\n warnOnceHere('settings_panel', 'settings_panel \"' + settings.settings_panel + '\" is not one of ' +\n PANEL_MODES.join(', ') + ': using offcanvas');\n return 'offcanvas';\n }\n\n /** A node's panel, wherever it is at the moment, or null. */\n function detailsOf(node) {\n return (node && detailsFor.get(node)) || null;\n }\n\n /** Where settings fields are found: the canvas, and the panel open outside it. */\n function settingsScope() {\n var scope = [canvas];\n\n if (openSettingsState && openSettingsState.mode !== 'inline') { scope.push(openSettingsState.details); }\n if (sidebarShown) { scope.push(sidebarShown.details); }\n\n return scope;\n }\n\n /** The gear: its node's panel, opened or closed; another node's closes first. */\n function toggleSettings(node, details, gear) {\n var mode = panelMode();\n\n if (mode === 'inline') {\n dom.toggle(details);\n return;\n }\n\n var same = openSettingsState && openSettingsState.details === details;\n closeSettings();\n if (!same) { openSettings(mode, node, details, gear); }\n }\n\n function openSettings(mode, node, details, gear) {\n var panel = settingsPanel(mode);\n var listening = new AbortController();\n\n openSettingsState = {\n mode: mode,\n node: node,\n details: details,\n home: details.parentElement,\n next: details.nextElementSibling,\n gear: gear,\n listening: listening,\n };\n\n dom.one(panel, '.ge-settings-title').textContent = t('panel.title', { kind: kindLabel(node) });\n dom.one(panel, '.ge-settings-body').appendChild(details);\n dom.show(details);\n dom.addClass(node, 'ge-settings-target');\n\n var signal = { signal: listening.signal };\n document.addEventListener('keydown', function(e) {\n // A dialog over the panel takes the Escape for itself\n if (e.key === 'Escape' && !dialogState) { closeSettings(); }\n }, signal);\n\n if (mode === 'offcanvas') {\n // From the bottom on a phone, from the side anywhere wider\n var narrow = window.innerWidth < 576;\n dom.toggleClass(panel, 'offcanvas-end', !narrow);\n dom.toggleClass(panel, 'offcanvas-bottom', narrow);\n dom.removeClass(panel, 'hiding');\n panel.getBoundingClientRect(); // So the slide in is a transition, not a jump\n dom.addClass(panel, 'show');\n } else if (mode === 'popover') {\n placePopover(panel, gear);\n dom.on(window, 'scroll resize', function() { placePopover(panel, gear); }, signal);\n\n // And again whenever what is in it changes size: the\n // Responsive section unfolding, a plugin swapping a field\n if (window.ResizeObserver) {\n openSettingsState.observer = new window.ResizeObserver(function() { placePopover(panel, gear); });\n openSettingsState.observer.observe(details);\n }\n // A press anywhere else puts it away, as a popover does\n dom.on(document, 'mousedown touchstart', function(e) {\n if (!dialogState && !panel.contains(e.target) && !gear.contains(e.target)) { closeSettings(); }\n }, signal);\n } else {\n showModal(panel, function() {\n if (openSettingsState && openSettingsState.mode === 'modal') { closeSettings(); }\n });\n }\n }\n\n /** Put what is open away, and its panel back in its drawer. */\n function closeSettings() {\n // A dialog opened from the panel goes with it\n closeDialog();\n\n var open = openSettingsState;\n if (!open) { return; }\n openSettingsState = null;\n\n var panel = settingsPanels[open.mode];\n open.listening.abort();\n if (open.observer) { open.observer.disconnect(); }\n\n if (open.mode === 'offcanvas') {\n dom.removeClass(panel, 'show');\n dom.addClass(panel, 'hiding');\n window.setTimeout(function() { dom.removeClass(panel, 'hiding'); }, 300);\n } else if (open.mode === 'popover') {\n dom.hide(panel);\n } else {\n hideModal(panel);\n }\n\n returnPanel(open);\n }\n\n /** A node's panel back where it was in its drawer, and the node no longer marked. */\n function returnPanel(open) {\n dom.removeClass(open.node, 'ge-settings-target');\n open.details.style.removeProperty('display');\n dom.dropEmptyStyle(open.details);\n\n // Where it was in its drawer, if the drawer is still there: a\n // node deleted while its settings were open took it with it\n if (open.home && dom.attached(open.home)) {\n if (open.next && open.next.parentElement === open.home) {\n open.home.insertBefore(open.details, open.next);\n } else {\n open.home.appendChild(open.details);\n }\n } else {\n open.details.remove();\n }\n }\n\n /** Built once per mode, on first use, and taken away by destroy() or setLocale(). */\n function settingsPanel(mode) {\n if (settingsPanels[mode]) { return settingsPanels[mode]; }\n\n var closeButton = function() {\n return dom.element('button', {\n type: 'button',\n 'class': 'btn-close ge-settings-close',\n 'aria-label': t('panel.close'),\n });\n };\n var panel;\n\n if (mode === 'offcanvas') {\n panel = dom.create('<div class=\"offcanvas offcanvas-end ge-settings-panel ge-settings-offcanvas\" tabindex=\"-1\" role=\"dialog\">' +\n '<div class=\"offcanvas-header\"><h5 class=\"offcanvas-title ge-settings-title\"></h5></div>' +\n '<div class=\"offcanvas-body ge-settings-body\"></div>' +\n '</div>');\n dom.one(panel, '.offcanvas-header').appendChild(closeButton());\n } else if (mode === 'popover') {\n panel = dom.create('<div class=\"popover bs-popover-bottom ge-settings-panel ge-settings-popover\" role=\"dialog\">' +\n '<div class=\"popover-arrow\"></div>' +\n '<div class=\"popover-header\"><span class=\"ge-settings-title\"></span></div>' +\n '<div class=\"popover-body ge-settings-body\"></div>' +\n '</div>');\n dom.one(panel, '.popover-header').appendChild(closeButton());\n dom.hide(panel);\n } else if (mode === 'sidebar') {\n panel = dom.create('<div class=\"offcanvas offcanvas-end ge-settings-panel ge-settings-sidebar\" tabindex=\"-1\" role=\"complementary\">' +\n '<div class=\"offcanvas-header\"><h5 class=\"offcanvas-title ge-settings-title\"></h5></div>' +\n '<div class=\"offcanvas-body ge-settings-body\"></div>' +\n '</div>');\n panel.id = 'ge-settings-sidebar-' + instanceId;\n dom.one(panel, '.offcanvas-header').appendChild(closeButton());\n // Beside the panel rather than in it: it stays on the window's edge when the panel is folded away\n settingsPanels['sidebar-toggle'] = document.body.appendChild(sidebarToggle(panel));\n } else {\n panel = dom.create('<div class=\"modal fade ge-settings-panel ge-settings-modal\" tabindex=\"-1\" role=\"dialog\" aria-hidden=\"true\">' +\n '<div class=\"modal-dialog modal-dialog-centered modal-dialog-scrollable\">' +\n '<div class=\"modal-content\">' +\n '<div class=\"modal-header\"><h5 class=\"modal-title ge-settings-title\"></h5></div>' +\n '<div class=\"modal-body ge-settings-body\"></div>' +\n '<div class=\"modal-footer\"></div>' +\n '</div>' +\n '</div>' +\n '</div>');\n dom.one(panel, '.modal-header').appendChild(closeButton());\n dom.one(panel, '.modal-footer').appendChild(dom.element('button', {\n type: 'button',\n 'class': 'btn btn-primary ge-settings-close',\n }, t('panel.done')));\n }\n\n dom.delegate(panel, 'click', '.ge-settings-close', function(e) {\n e.preventDefault();\n if (mode === 'sidebar') { changeSelection(null); } else { closeSettings(); }\n });\n\n settingsPanels[mode] = document.body.appendChild(panel);\n return panel;\n }\n\n function removeSettingsPanels() {\n closeSettings();\n unshowSidebar();\n dom.removeClass(document.documentElement, 'ge-sidebar-open');\n\n Object.keys(settingsPanels).forEach(function(mode) {\n if (mode === 'modal') {\n retireModal(settingsPanels[mode]);\n } else {\n settingsPanels[mode].remove();\n }\n });\n Object.keys(settingsPanels).forEach(function(mode) { removeBackdrop(settingsPanels[mode]); });\n settingsPanels = {};\n }\n\n /* --------------------------------------------------------------\n * settings_panel: 'sidebar'. An offcanvas that stays: there while\n * the canvas is edited, making room for itself on the page, with the\n * settings of the node that is selected in it - or, with none, a\n * message, or what the host or a plugin put there instead.\n *\n * The panels are the same ones: the selected node's moves into the\n * sidebar and goes back to its drawer when another is selected, so\n * ge.detailsOf(node) finds it either way. Folded away, the panel\n * slides out and its button stays on the window's edge.\n * -------------------------------------------------------------- */\n\n var SIDEBAR_MIN_WIDTH = 576; // Bootstrap's sm: narrower than that, the sidebar covers the page instead of making room\n var sidebarShown = null; // The selected node's panel while it is in the sidebar: { node, details, home, next }\n var sidebarEmpty = null; // What the sidebar shows while nothing is selected: { body }\n\n function isEditing() {\n return dom.hasClass(canvas, 'ge-editing');\n }\n\n function sidebarToggle(panel) {\n var button = dom.element('button', { type: 'button', 'class': 'ge-sidebar-toggle', 'aria-controls': panel.id });\n button.appendChild(dom.element('i'));\n button.addEventListener('click', function() { foldSidebar(!sidebarCollapsed); });\n return button;\n }\n\n function foldSidebar(collapsed) {\n sidebarCollapsed = collapsed;\n applySidebar();\n }\n\n /** The panel and its button as `sidebarCollapsed` says. */\n function applySidebar() {\n var panel = settingsPanels.sidebar;\n var toggle = settingsPanels['sidebar-toggle'];\n if (!panel) { return; }\n\n var open = !sidebarCollapsed;\n\n if (open && !dom.hasClass(panel, 'show')) {\n dom.removeClass(panel, 'hiding');\n panel.getBoundingClientRect(); // So the slide in is a transition, not a jump\n dom.addClass(panel, 'show');\n } else if (!open && dom.hasClass(panel, 'show')) {\n dom.removeClass(panel, 'show');\n dom.addClass(panel, 'hiding');\n window.setTimeout(function() { dom.removeClass(panel, 'hiding'); }, 300);\n }\n\n var label = open ? t('panel.collapse') : t('panel.expand');\n toggle.setAttribute('aria-expanded', open ? 'true' : 'false');\n toggle.setAttribute('aria-label', label);\n toggle.setAttribute('title', label);\n dom.one(toggle, 'i').className = 'bi ' + (open ? 'bi-chevron-right' : 'bi-chevron-left');\n\n reserveSidebarRoom();\n }\n\n /** The page makes room for the sidebar only while it is edited, unfolded, and the window is wide enough to have room. */\n function reserveSidebarRoom() {\n dom.toggleClass(document.documentElement, 'ge-sidebar-open',\n !!settingsPanels.sidebar && isEditing() && !sidebarCollapsed && window.innerWidth >= SIDEBAR_MIN_WIDTH);\n }\n\n /** Editing starts, or starts again: the sidebar is there, showing what is selected. */\n function showSidebar() {\n if (panelMode() !== 'sidebar') { return; }\n\n var panel = settingsPanel('sidebar');\n if (sidebarCollapsed === null) { sidebarCollapsed = window.innerWidth < SIDEBAR_MIN_WIDTH; }\n\n panel.style.removeProperty('display');\n settingsPanels['sidebar-toggle'].style.removeProperty('display');\n renderSidebar();\n applySidebar();\n }\n\n /** Editing stops: out of sight, with the selected node's panel back in its drawer. The selection stays. */\n function hideSidebar() {\n unshowDetails();\n\n var panel = settingsPanels.sidebar;\n if (!panel) { return; }\n\n panel.style.display = 'none';\n settingsPanels['sidebar-toggle'].style.display = 'none';\n dom.removeClass(document.documentElement, 'ge-sidebar-open');\n }\n\n function setSidebarTitle(text) {\n var panel = settingsPanels.sidebar;\n dom.one(panel, '.ge-settings-title').textContent = text;\n panel.setAttribute('aria-label', text);\n }\n\n function unshowDetails() {\n var shown = sidebarShown;\n sidebarShown = null;\n if (shown) { returnPanel(shown); }\n }\n\n /** Whatever the sidebar holds out of it: the panel to its drawer, the empty content out of the body, not destroyed. */\n function unshowSidebar() {\n unshowDetails();\n\n if (sidebarEmpty) {\n sidebarEmpty.body.remove();\n sidebarEmpty = null;\n }\n }\n\n /** What the sidebar shows is what is selected; nothing to do when it already does. */\n function renderSidebar() {\n var panel = settingsPanels.sidebar;\n if (!panel || !isEditing()) { return; }\n\n var details = selected ? detailsOf(selected) : null;\n if (details ? sidebarShown && sidebarShown.details === details : !sidebarShown && sidebarEmpty) { return; }\n\n unshowSidebar();\n var holder = dom.one(panel, '.ge-settings-body');\n\n if (!details) {\n var content = emptyContent();\n var body = content ? content.body : dom.element('p', { 'class': 'ge-sidebar-empty' }, t('panel.sidebar_empty'));\n\n setSidebarTitle(content ? content.title : t('panel.sidebar_title'));\n holder.appendChild(body);\n sidebarEmpty = { body: body };\n return;\n }\n\n sidebarShown = { node: selected, details: details, home: details.parentElement, next: details.nextElementSibling };\n setSidebarTitle(t('panel.title', { kind: kindLabel(selected) }));\n holder.appendChild(details);\n dom.show(details);\n dom.addClass(selected, 'ge-settings-target');\n }\n\n /**\n * What the sidebar shows with nothing selected, other than its\n * message: the host's sidebar.empty, else the first plugin's\n * sidebarEmpty, as { title, body }. Null for the message.\n */\n function emptyContent() {\n var fromHost = settings.sidebar.empty;\n var found = null;\n\n if (typeof fromHost === 'function') {\n found = emptyContentOf(fromHost(instance), function(result) { return result.title; });\n } else if (fromHost !== null && fromHost !== undefined) {\n warnOnceHere('sidebar.empty', 'sidebar.empty is a function(ge) returning { title, body }, not ' +\n typeof fromHost + ': ignored');\n }\n\n [CONTAINERS, FEATURES, UTILITIES].forEach(function(registry) {\n Object.keys(registry).forEach(function(name) {\n var plugin = registry[name];\n if (found || !plugin.sidebarEmpty) { return; }\n\n found = emptyContentOf(plugin.sidebarEmpty(pluginHandle), function(result) {\n return typeof result.titleKey === 'string' && result.titleKey !== '' ? t(result.titleKey) : '';\n });\n });\n });\n\n return found;\n }\n\n /** An answer of sidebar.empty or sidebarEmpty as { title, body }, or null when it has no body to show. */\n function emptyContentOf(result, titleOf) {\n if (!result || !result.body || result.body.nodeType !== 1) { return null; }\n\n var title = titleOf(result);\n return { title: typeof title === 'string' && title !== '' ? title : t('panel.sidebar_title'), body: result.body };\n }\n\n /**\n * The node at `target` whose settings the sidebar shows: the\n * innermost one, its drawer included. A text's drawer is beside it\n * rather than in it.\n */\n function settingsNodeAt(target) {\n var drawer = dom.closest(target, '.ge-tools-drawer', canvas);\n\n if (drawer) {\n var home = drawer.parentElement;\n var owner = detailsFor.has(home) ? home : dom.children(home).filter(function(each) {\n return detailsFor.has(each);\n })[0];\n if (owner) { return owner; }\n }\n\n for (var node = target; node && node !== canvas; node = node.parentElement) {\n if (detailsFor.has(node)) { return node; }\n }\n\n return null;\n }\n\n /** The one way the selection changes, told only when it does. */\n function changeSelection(node) {\n if (node === selected) { return; }\n\n var from = selected;\n selected = node;\n renderSidebar();\n\n emit('selection-change', { canvas: canvas, node: node, from: from });\n }\n\n /**\n * Under the gear, or over it when there is more room there, inside\n * the window, and no taller than the room it has: past that its body\n * scrolls.\n */\n function placePopover(panel, gear) {\n if (!dom.attached(gear)) { return; }\n\n dom.show(panel);\n\n var tool = gear.getBoundingClientRect();\n var gap = 8;\n var body = dom.child(panel, '.popover-body');\n body.style.removeProperty('max-height');\n var width = dom.outerWidth(panel);\n var height = dom.outerHeight(panel);\n var roomBelow = window.innerHeight - tool.bottom - 2 * gap;\n var roomAbove = tool.top - 2 * gap;\n var below = height <= roomBelow || roomBelow >= roomAbove;\n var room = below ? roomBelow : roomAbove;\n\n if (height > room) {\n dom.css(body, { 'max-height': Math.max(120, room - (height - dom.outerHeight(body))) });\n height = dom.outerHeight(panel);\n }\n\n var top = below ? tool.bottom + gap : tool.top - gap - height;\n var left = Math.max(gap, Math.min(tool.left + tool.width / 2 - 24, window.innerWidth - width - gap));\n\n dom.toggleClass(panel, 'bs-popover-bottom', below);\n dom.toggleClass(panel, 'bs-popover-top', !below);\n dom.css(panel, { top: top + window.pageYOffset, left: left + window.pageXOffset });\n\n // The arrow points at the gear, wherever the popover had to go\n dom.css(dom.child(panel, '.popover-arrow'), {\n left: Math.max(gap, Math.min(tool.left + tool.width / 2 - left - 8, width - 24)),\n });\n }\n\n /**\n * Bootstrap's modal ignores a hide while it is still fading in, and a\n * show while it is fading out, so the editor asks for what it wants\n * and has it done once the running transition ends: a panel closed as\n * it opens - getHtml, a second click - would otherwise stay open, and\n * empty. A hide Bootstrap starts itself, from Escape or the backdrop,\n * calls `dismissed`, as the close button does: the settings modal\n * closes the settings, the dialog closes the dialog.\n *\n * Without Bootstrap's javascript the modal is shown by hand, over a\n * backdrop of the editor's own that dismisses it when clicked.\n */\n function showModal(panel, dismissed) {\n var Modal = modalLibrary();\n var state = modalState.get(panel);\n\n if (!state) {\n state = { wanted: null, busy: false, backdrop: null, dismissed: dismissed };\n modalState.set(panel, state);\n }\n state.dismissed = dismissed;\n\n if (!Modal) {\n if (!state.backdrop) {\n state.backdrop = dom.element('div', { 'class': 'modal-backdrop fade show ge-settings-backdrop' });\n state.backdrop.addEventListener('click', function() { state.dismissed(); });\n document.body.appendChild(state.backdrop);\n }\n dom.addClass(panel, 'show');\n panel.style.display = 'block';\n panel.removeAttribute('aria-hidden');\n return;\n }\n\n var modal = Modal.getOrCreateInstance(panel);\n\n if (!state.watched) {\n state.watched = true;\n trackModal(panel);\n\n panel.addEventListener('hide.bs.modal', function() {\n // Not asked for: Escape or the backdrop\n if (state.wanted === 'open') {\n state.wanted = 'closed';\n state.busy = true;\n }\n });\n panel.addEventListener('shown.bs.modal', function() {\n state.busy = false;\n if (state.wanted === 'closed') { hideModal(panel); }\n });\n panel.addEventListener('hidden.bs.modal', function() {\n state.busy = false;\n if (state.wanted === 'open') {\n showModal(panel, state.dismissed);\n } else {\n state.dismissed();\n }\n });\n }\n\n state.wanted = 'open';\n if (!state.busy) {\n state.busy = true;\n modal.show();\n }\n }\n\n function hideModal(panel) {\n var Modal = modalLibrary();\n var state = modalState.get(panel);\n\n if (!state) { return; }\n state.wanted = 'closed';\n\n if (!Modal) {\n if (state.backdrop) { state.backdrop.remove(); state.backdrop = null; }\n dom.removeClass(panel, 'show');\n panel.style.removeProperty('display');\n panel.setAttribute('aria-hidden', 'true');\n return;\n }\n\n // Already out of sight - Bootstrap hid it itself, and this is its\n // hidden event closing the settings - and nothing is under way:\n // a hide now would be ignored, and no event would come to say so\n if (!state.busy && dom.hasClass(panel, 'show')) {\n state.busy = true;\n Modal.getOrCreateInstance(panel).hide();\n }\n }\n\n /** A modal's hand made backdrop goes with it. */\n function removeBackdrop(panel) {\n var state = modalState.get(panel);\n if (state && state.backdrop) { state.backdrop.remove(); state.backdrop = null; }\n }\n\n /* --------------------------------------------------------------\n * The dialog: a modal of the editor's own, over whatever settings\n * panel is open, for what does not fit in one. A plugin's section\n * of the panel opens in it when the panel is a popover or inline,\n * and a plugin can open one itself through ge.openDialog.\n *\n * What it shows is borrowed: the body goes into the dialog when it\n * opens and back where it was when it closes, so everything that\n * finds it through its node keeps working. One per editor, built\n * on first use, outside the canvas.\n * -------------------------------------------------------------- */\n\n var dialogPanel = null;\n var dialogState = null; // What is open: { body, home, next, opener, listening }\n\n function dialog() {\n if (dialogPanel) { return dialogPanel; }\n\n dialogPanel = dom.create('<div class=\"modal fade ge-dialog\" tabindex=\"-1\" role=\"dialog\" aria-hidden=\"true\">' +\n '<div class=\"modal-dialog modal-dialog-centered modal-dialog-scrollable\">' +\n '<div class=\"modal-content\">' +\n '<div class=\"modal-header\"><h5 class=\"modal-title ge-dialog-title\"></h5></div>' +\n '<div class=\"modal-body ge-dialog-body\"></div>' +\n '<div class=\"modal-footer\"></div>' +\n '</div>' +\n '</div>' +\n '</div>');\n dom.one(dialogPanel, '.modal-header').appendChild(dom.element('button', {\n type: 'button',\n 'class': 'btn-close ge-dialog-close',\n 'aria-label': t('panel.close'),\n }));\n dom.one(dialogPanel, '.modal-footer').appendChild(dom.element('button', {\n type: 'button',\n 'class': 'btn btn-primary ge-dialog-close',\n }, t('panel.done')));\n\n dom.delegate(dialogPanel, 'click', '.ge-dialog-close', function(e) {\n e.preventDefault();\n closeDialog();\n });\n\n return document.body.appendChild(dialogPanel);\n }\n\n /**\n * ge.openDialog(title, body, opener): show `body` in the dialog. One\n * already open closes first. `opener`, when given, has the focus back\n * when it closes.\n */\n function openDialog(title, body, opener) {\n closeDialog();\n\n var panel = dialog();\n var listening = new AbortController();\n\n dialogState = {\n body: body,\n home: body.parentElement,\n next: body.nextElementSibling,\n opener: opener || document.activeElement,\n listening: listening,\n };\n\n dom.one(panel, '.ge-dialog-title').textContent = title;\n dom.one(panel, '.ge-dialog-body').appendChild(body);\n dom.show(body);\n\n // Bootstrap's modal takes its own Escape; a hand made one does not\n if (!modalLibrary()) {\n document.addEventListener('keydown', function(e) {\n if (e.key === 'Escape') { closeDialog(); }\n }, { signal: listening.signal });\n }\n\n // Bootstrap puts a popover over a modal: the panel the dialog was\n // opened from goes under its backdrop while it is up\n Object.keys(settingsPanels).forEach(function(mode) {\n dom.addClass(settingsPanels[mode], 'ge-under-dialog');\n });\n\n showModal(panel, function() { closeDialog(); });\n }\n\n /** ge.closeDialog(): put the dialog away, and what it showed back where it was. */\n function closeDialog() {\n var open = dialogState;\n if (!open) { return; }\n dialogState = null;\n\n open.listening.abort();\n hideModal(dialogPanel);\n Object.keys(settingsPanels).forEach(function(mode) {\n dom.removeClass(settingsPanels[mode], 'ge-under-dialog');\n });\n\n dom.hide(open.body);\n if (open.home && dom.attached(open.home)) {\n if (open.next && open.next.parentElement === open.home) {\n open.home.insertBefore(open.body, open.next);\n } else {\n open.home.appendChild(open.body);\n }\n } else {\n open.body.remove();\n }\n\n if (open.opener && dom.attached(open.opener) && open.opener.focus) { open.opener.focus(); }\n }\n\n function removeDialog() {\n closeDialog();\n if (!dialogPanel) { return; }\n\n removeBackdrop(dialogPanel);\n retireModal(dialogPanel);\n dialogPanel = null;\n }\n\n /** What a panel's title calls a node. */\n function kindLabel(node) {\n var kind = kindOf(node);\n\n if (CONTAINERS[kind] && CONTAINERS[kind].labelKey) { return t(CONTAINERS[kind].labelKey); }\n\n var paneLabel = Object.keys(CONTAINERS).filter(function(type) {\n return CONTAINERS[type].paneKind === kind && CONTAINERS[type].paneLabelKey;\n })[0];\n if (paneLabel) { return t(CONTAINERS[paneLabel].paneLabelKey); }\n\n switch (kind) {\n case 'row': return t('panel.kind_row');\n case 'column': return t('panel.kind_column');\n case 'text': return t('panel.kind_text');\n case 'element': return t('panel.kind_element');\n case 'section': return t('panel.kind_section');\n case 'tab': return t('panel.kind_tab');\n case 'accordion-item': return t('panel.kind_accordion_item');\n default: return kind;\n }\n }\n\n /**\n * Make sure every column is marked as one, and that a column with no\n * sizing at all gets some.\n *\n * Deliberately conservative: a column that carries any size class is\n * left exactly as authored. Seeding every tier would put six classes\n * on every column now that there are six tiers, and the smallest tier\n * already applies to the wider ones, so one class is enough for a\n * column that had none.\n */\n function addAllColClasses() {\n dom.all(canvas, '.column, div[class*=\"col-\"], div.col').forEach(function(col) {\n dom.addClass(col, 'column');\n\n // A column in a row with row-cols is sized by its row\n if (sizedTiers(col).length || hasRowCols(col.parentElement)) { return; }\n\n setSize(col, BREAKPOINTS[0], MAX_COL_SIZE);\n });\n }\n\n /* --------------------------------------------------------------\n * Columns per row: row-cols-*.\n *\n * A row's row-cols class gives every child an equal share of a\n * line, and a column's own size class takes that share's place.\n * Which of the two wins at a breakpoint is settled the way\n * Bootstrap's css settles it: the class from the wider breakpoint,\n * and at one breakpoint col loses to row-cols, which loses to\n * col-auto and col-N - the order Bootstrap writes their rules in.\n * -------------------------------------------------------------- */\n\n function hasRowCols(row) {\n return dom.hasClass(row, 'row') && BREAKPOINTS.some(function(tier) {\n return ROW_COLS_VALUES.some(function(value) { return dom.hasClass(row, rowColsClass(tier, value)); });\n });\n }\n\n /** The row-cols class that applies to a row at a tier, as { tier, value }, or null. */\n function rowColsSource(row, tier) {\n if (!dom.hasClass(row, 'row')) { return null; }\n\n for (var i = BREAKPOINTS.indexOf(tier); i >= 0; i--) {\n for (var v = 0; v < ROW_COLS_VALUES.length; v++) {\n if (dom.hasClass(row, rowColsClass(BREAKPOINTS[i], ROW_COLS_VALUES[v]))) {\n return { tier: i, value: ROW_COLS_VALUES[v] };\n }\n }\n }\n\n return null;\n }\n\n /** The column's own size that applies at a tier, as { tier, size }, or null. */\n function columnSource(col, tier) {\n for (var i = BREAKPOINTS.indexOf(tier); i >= 0; i--) {\n var size = getSize(col, BREAKPOINTS[i]);\n if (size !== null) { return { tier: i, size: size }; }\n }\n\n return null;\n }\n\n /**\n * The row-cols class that sizes this column at a tier, or null when\n * the column's own size does.\n */\n function rowColsWinner(col, tier) {\n var row = rowColsSource(col.parentElement, tier);\n if (!row) { return null; }\n\n var own = columnSource(col, tier);\n if (!own || row.tier > own.tier) { return row; }\n\n return row.tier === own.tier && own.size === 'equal' ? row : null;\n }\n\n /** A column's share of a line when its row sizes it, in units: auto has no number. */\n function rowColsUnits(winner) {\n return winner.value === 'auto' ? 0 : MAX_COL_SIZE / parseInt(winner.value, 10);\n }\n\n /**\n * What a breakpoint view shows of the row-cols a column is under. The\n * view narrows the canvas, not the window, and Bootstrap's\n * .row-cols-md-3 > * answers to the window - and to nothing the\n * preview can put on the row, since it styles the row's children.\n */\n function rowColsPreview(col, tier) {\n var winner = rowColsWinner(col, tier);\n\n if (winner) {\n return {\n flex: '0 0 auto',\n width: winner.value === 'auto' ? 'auto' : (100 / parseInt(winner.value, 10)) + '%',\n 'max-width': '100%',\n };\n }\n\n // A wider breakpoint's row-cols is live in a wide window; a\n // column with no size of its own here is a full width one\n if (hasRowCols(col.parentElement) && !columnSource(col, tier)) {\n return { flex: '0 0 auto', width: '100%', 'max-width': '100%' };\n }\n\n return {};\n }\n\n /**\n * The badge on a row whose columns are sized by row-cols in the view,\n * and in the all view by its row-cols with no breakpoint.\n */\n function markRowCols(scope) {\n dom.selfAndAll(scope, '.row').forEach(function(row) {\n var source = settings.row_cols === false ? null : (curView === ALL_VIEW\n ? (rowColsSource(row, BREAKPOINTS[0]) || null)\n : rowColsSource(row, breakpoint(curView)));\n\n if (!source) {\n row.removeAttribute('data-ge-row-cols');\n } else {\n row.setAttribute('data-ge-row-cols', rowColsLabel(source.value));\n }\n });\n }\n\n function rowColsLabel(value) {\n return value === 'auto' ? t('badge.row_cols_auto') : t('badge.row_cols', { count: value });\n }\n\n /** The core's family for the field in a row's panel. */\n function rowColsFamily() {\n return {\n name: 'row-cols',\n prefix: 'row-cols',\n values: ROW_COLS_VALUES,\n appliesTo: ['row'],\n labelKey: 'utility.row_cols',\n };\n }\n\n /* --------------------------------------------------------------\n * The sizing core.\n *\n * Everything that reads or writes a size or an offset class goes\n * through here: the width and indent tools, drag resize,\n * createColumn and the getHtml cleanup. One place owns the class\n * names, the 12 unit budget and what an absent class means.\n * -------------------------------------------------------------- */\n\n /**\n * A column's size at one tier: a number of units, `equal`, `auto`, or\n * null when that tier says nothing.\n */\n function getSize(col, tier) {\n var units = readUnits(col, tier.colPrefix);\n if (units !== null) { return units; }\n\n if (dom.hasClass(col, sizeClass(tier, 'auto'))) { return 'auto'; }\n if (dom.hasClass(col, sizeClass(tier, 'equal'))) { return 'equal'; }\n\n return null;\n }\n\n /** The units a column is indented by at one tier, or null. */\n function getOffset(col, tier) {\n return readUnits(col, tier.offsetPrefix);\n }\n\n /**\n * What actually applies at a tier: its own class, or the nearest\n * smaller tier that has one, because that is how Bootstrap cascades.\n * Null when no tier below it says anything either.\n *\n * Not a \"return the first thing I found\" fallback: it walks the tiers\n * downward from the one asked about, so an offset lookup can never\n * answer with a size, and a lookup for one tier can never answer with\n * a wider tier's value.\n */\n function getEffectiveSize(col, tier) {\n return readEffective(col, tier, getSize);\n }\n\n function getEffectiveOffset(col, tier) {\n return readEffective(col, tier, getOffset);\n }\n\n function readEffective(col, tier, read) {\n for (var i = BREAKPOINTS.indexOf(tier); i >= 0; i--) {\n var units = read(col, BREAKPOINTS[i]);\n if (units !== null) { return units; }\n }\n\n return null;\n }\n\n function readUnits(col, prefix) {\n var match = new RegExp('(?:^|\\\\s)' + prefix + '(\\\\d+)(?:\\\\s|$)').exec(col.getAttribute('class') || '');\n return match ? parseInt(match[1], 10) : null;\n }\n\n function writeUnits(col, prefix, units) {\n var classes = (col.getAttribute('class') || '').split(/\\s+/).filter(function(name) {\n return name !== '' && !new RegExp('^' + prefix + '\\\\d+$').test(name);\n });\n\n if (units !== null) { classes.push(prefix + units); }\n\n col.setAttribute('class', classes.join(' '));\n }\n\n /** One size per tier: writing a size takes whatever size the tier had off. */\n function setSize(col, tier, size) {\n writeUnits(col, tier.colPrefix, null);\n FLEX_SIZES.forEach(function(flex) { dom.removeClass(col, sizeClass(tier, flex)); });\n\n if (size !== null && size !== undefined) { dom.addClass(col, sizeClass(tier, size)); }\n }\n\n /** An offset of 0 is written as no class at all, which is what it means. */\n function setOffset(col, tier, units) {\n writeUnits(col, tier.offsetPrefix, units ? units : null);\n }\n\n /** The tiers a column carries an explicit size for. */\n function sizedTiers(col) {\n return BREAKPOINTS.filter(function(tier) {\n return getSize(col, tier) !== null;\n });\n }\n\n /**\n * The units left in a row at one tier, counting every sibling's size\n * and offset. What \"hold shift for max\" grows into.\n */\n function spare(row, tier, ignore) {\n var used = 0;\n\n dom.children(row, '.column').forEach(function(sibling) {\n if (ignore && sibling === ignore) { return; }\n\n // An equal or auto column takes what is left, so it uses none;\n // one its row sizes uses its share of the line\n var winner = rowColsWinner(sibling, tier);\n var size = winner ? rowColsUnits(winner) : getEffectiveSize(sibling, tier);\n used += (isUnits(size) ? size : 0) + (getEffectiveOffset(sibling, tier) || 0);\n });\n\n return MAX_COL_SIZE - used;\n }\n\n /**\n * The 12 unit budget, in one place: a column's size plus its offset\n * never exceeds 12 at any tier.\n *\n * Which of the two gives way is the caller's decision, expressed by\n * which one it marks as leading. Growing an offset shrinks the column;\n * growing a column with no room left is refused, so the tool visibly\n * does nothing rather than quietly rewriting an offset the user set.\n */\n function clamp(request) {\n var size = request.size === null || request.size === undefined ? null : request.size;\n var offset = request.offset === null || request.offset === undefined ? 0 : request.offset;\n\n offset = Math.min(Math.max(offset, 0), MAX_COL_OFFSET);\n\n if (size === null || !isUnits(size)) { return { size: size, offset: offset, refused: false }; }\n\n size = Math.min(Math.max(size, 1), MAX_COL_SIZE);\n\n if (size + offset <= MAX_COL_SIZE) {\n return { size: size, offset: offset, refused: false };\n }\n\n if (request.leading === 'offset') {\n return { size: MAX_COL_SIZE - offset, offset: offset, refused: false };\n }\n\n return { size: null, offset: offset, refused: true };\n }\n\n /**\n * Drag resize leaves an inline pixel width behind: the column follows\n * the pointer in pixels while the gesture lasts. It does not belong in\n * the markup a host saves, or in the canvas once the size class has\n * been written.\n */\n function stripPixelWidths(scope) {\n dom.selfAndAll(scope, '.column').forEach(function(col) {\n dom.css(col, { width: '', height: '', left: '', top: '' });\n\n // Clearing the last property leaves style=\"\" behind, which is\n // an editor leftover like any other\n dom.dropEmptyStyle(col);\n });\n }\n\n /**\n * A group name, scoped to this editor.\n *\n * Two editors on one page must not drag into each other, since a node\n * carries its drawer - and the events that go with it - from the\n * editor that made it.\n */\n function groupName(name) {\n return 'ge-' + name + '-' + instanceId;\n }\n\n /**\n * What the canvas, the columns and the plugins' regions move: rows,\n * text blocks and containers, and whatever blocks a feature adds -\n * the sections plugin's sections. A content area is a block through\n * the text block around it while editing, and on its own before.\n */\n function blockSelector() {\n return ['.row', '.ge-text-block', '.ge-content', '[data-ge-container]']\n .concat(pluginHooks('blocks')).join(', ');\n }\n\n /** A selector every feature plugin may contribute to, under one name. */\n function pluginHooks(name) {\n return Object.keys(FEATURES).map(function(key) {\n return FEATURES[key][name] || null;\n }).filter(function(hook) { return hook !== null; });\n }\n\n /**\n * Whether a region will have a block dropped in it. Every block goes\n * everywhere unless a feature says otherwise: a section only on the\n * canvas, and only rows in a section.\n */\n function acceptsBlock(region, node) {\n var accepted = true;\n\n Object.keys(FEATURES).forEach(function(name) {\n var feature = FEATURES[name];\n if (accepted && feature.accepts && feature.accepts(region, node) === false) { accepted = false; }\n });\n\n return accepted;\n }\n\n /** What must never start a drag, whatever the handle is. */\n function dragCancelSelector() {\n return settings.drag_handle === 'drawer'\n // With the whole drawer as the handle, the tools inside it are\n // still tools: a drag starting on one would swallow its click,\n // and the settings panel has fields to type in\n // - the info tools excepted, which do nothing when clicked:\n // a text's drawer is small and made of little but tools, and\n // with those turned away as well there was nothing to hold\n ? '.ge-tools-drawer > a:not(.ge-text-info):not(.ge-element-info), .ge-details, ' +\n 'input, textarea, button, select, option'\n : 'input, textarea, button, select, option';\n }\n\n /**\n * Every sortable list the editor makes, core's and a plugin's alike,\n * is made here.\n *\n * A caller says what moves (`draggable`) and what the list connects to\n * (`group`, or none for a list that sorts only within itself); the\n * handle, the filter, the callbacks and the drag settings are this\n * function's business. That is the whole point of it: the toolkit\n * underneath is named in one place, so replacing it is one function\n * and not thirty call sites.\n *\n * `lists` is an element or an array of them; `options.accepts`, when\n * given, is asked (list, item) with elements.\n */\n function sortable(lists, options) {\n var Sortable = sortableLibrary();\n\n lists = Array.isArray(lists) ? lists : (lists ? [lists] : []);\n if (!lists.length || !Sortable) { return; }\n\n var wholeDrawer = settings.drag_handle === 'drawer';\n var cancel = dragCancelSelector();\n var soloGroup = 0;\n\n lists.forEach(function(list) {\n // A list with no group sorts only within itself, which is what\n // a tab strip wants: a name of its own, closed both ways\n var group = options.group\n ? { name: groupName(options.group) }\n : { name: groupName(options.draggable + '-' + (++soloGroup)), pull: false, put: false };\n\n // A list may turn some of its group's items away. A put\n // function replaces SortableJS's own test that the item comes\n // from the same group, so it makes that test too: without it\n // a column would drop into the canvas, or into another editor\n if (options.group && options.accepts) {\n group.put = function(to, from, dragged) {\n return from.options.group.name === group.name && options.accepts(to.el, dragged);\n };\n }\n\n sortables.push(Sortable.create(list, Object.assign({\n group: group,\n draggable: options.draggable,\n handle: wholeDrawer ? '.ge-tools-drawer' : '.ge-tools-drawer .ge-move',\n\n /**\n * Two refusals in one, because SortableJS asks once.\n *\n * A tool or a form field never starts a drag, as the\n * cancel list said before. And only a direct child of\n * this list moves: the selector is matched against every\n * descendant, so without this the canvas would pick up a\n * row nested three columns down and drag that.\n */\n filter: function(e, item) {\n if (dom.closest(e.target, cancel, list)) { return true; }\n\n return !item || item.parentNode !== list;\n },\n\n // A filtered pointerdown is still a click on a tool\n preventOnFilter: false,\n\n // The HTML5 drag and drop API cannot be driven by\n // synthetic events, so the tests could not exist without\n // this; it also gives one helper across browsers\n forceFallback: true,\n\n // The copy that follows the pointer is appended to the\n // list the drag started in rather than to the body: it is\n // positioned fixed either way, and inside the canvas it\n // looks like what it is a copy of. On the body none of the\n // editing styles reached it - its drawers came out\n // unstyled, their settings panels open.\n fallbackOnBody: false,\n\n ghostClass: 'ge-drag-placeholder',\n chosenClass: 'ge-drag-chosen',\n dragClass: 'ge-drag-helper',\n fallbackClass: 'ge-drag-helper',\n\n animation: settings.drag.animation,\n\n // One delay, which applies to both gestures or to touch\n // alone: a touch drag that starts instantly takes the\n // page's scrolling with it, a mouse drag has no such\n // problem, and asking for `delay` means asking for both\n delay: settings.drag.delay || settings.drag.touch_delay,\n delayOnTouchOnly: !settings.drag.delay,\n\n touchStartThreshold: settings.drag.threshold,\n scroll: settings.drag.scroll,\n\n onStart: sortStart,\n onEnd: sortEnd,\n }, options.options || {})));\n });\n }\n\n function makeSortable() {\n if (!sortableLibrary()) {\n warnOnceHere('sortable_missing', t('error.sortable_missing'));\n return;\n }\n\n sortable(dom.all(canvas, '.row'), {\n draggable: '.column',\n group: 'column',\n });\n\n sortable([canvas].concat(dom.all(canvas, '.column')), {\n draggable: blockSelector(),\n group: 'block',\n accepts: acceptsBlock,\n });\n\n // A plugin's region can be a block itself - a section is both -\n // and SortableJS tests a list's own element against the draggable\n // selector when it counts the list's children, so every child of\n // a section would count as a block, its drawer first. '>' is\n // SortableJS for \"direct children only\", which the list is not.\n var regions = pluginHooks('regions');\n if (regions.length) {\n sortable(dom.all(canvas, regions.join(', ')), {\n draggable: '>' + blockSelector(),\n group: 'block',\n accepts: acceptsBlock,\n });\n }\n\n // A plugin makes its own: only it knows which of its parts move\n plugins('onSortable', sortable);\n }\n\n /**\n * A drag cannot be refused once it has started, so a canceled\n * before-move is remembered here and undone on drop (spec 2.4). The\n * node carries the mark, because with connected lists the drop is not\n * always reported by the list that started the drag.\n */\n function sortStart(e) {\n var node = e.item;\n var from = positionOf(node);\n var subject = moveSubject(node);\n var move = { from: from, canceled: false };\n\n moves.set(node, move);\n\n operate(function() {\n var moving = emit('before-move', payloadFor(subject.kind, subject.node, {\n parent: from.parent,\n source: 'dragdrop',\n from: from,\n }));\n\n if (!moving) { move.canceled = true; }\n });\n }\n\n /**\n * What a drag reports as moving. A text block is the editor's own\n * wrapper, so what moved is the content area inside it.\n */\n function moveSubject(item) {\n var node = dom.hasClass(item, 'ge-text-block') ? (dom.child(item, '.ge-content') || item) : item;\n\n return { kind: kindOf(node), node: node };\n }\n\n /** Put a node back where a refused drag found it. */\n function putBack(node, from) {\n var siblings = dom.children(from.parent).filter(function(child) {\n return child !== node && !dom.hasClass(child, 'ge-tools-drawer');\n });\n\n if (!siblings.length || from.index >= siblings.length) {\n from.parent.appendChild(node);\n } else {\n from.parent.insertBefore(node, siblings[from.index]);\n }\n }\n\n function sortEnd(e) {\n var node = e.item;\n var move = moves.get(node);\n var from = move ? move.from : positionOf(node);\n\n moves.delete(node);\n\n if (move && move.canceled) {\n putBack(node, from);\n return;\n }\n\n var to = positionOf(node);\n if (to.parent === from.parent && to.index === from.index) {\n return; // A drag that went nowhere is not a move\n }\n\n var container = dom.closest(node, '[data-ge-container]');\n var definition = CONTAINERS[containerTypeOf(container)];\n if (definition && definition.afterPaneMove) {\n definition.afterPaneMove(container, node, from);\n }\n\n // No init() here, unlike an add: the node brought its drawer\n // with it, and the drag is still being finished, so this is the\n // wrong moment to rebuild the lists it is using.\n var subject = moveSubject(node);\n\n operate(function() {\n emit('after-move', payloadFor(subject.kind, subject.node, {\n parent: to.parent,\n source: 'dragdrop',\n from: from,\n to: to,\n container: container || undefined,\n }));\n });\n }\n\n /**\n * Resizing a column by dragging its edge.\n *\n * The handle sits on the column's edge and the sort handle is the\n * drawer, so the two gestures never fight over the same pixels. The\n * column follows the pointer in pixels while dragging, the drawer says\n * which class it would land on, and the pixels are snapped to whole\n * units and thrown away on drop.\n */\n function makeResizable() {\n if (!settings.resize.enabled) { return; }\n\n dom.all(canvas, '.column').forEach(function(col) {\n if (dom.child(col, '.ge-resize-handle')) { return; }\n\n var drawer = dom.child(col, '.ge-tools-drawer');\n if (drawer) { drawer.appendChild(dom.element('span', { 'class': 'ge-resize-size' })); }\n\n resizeEdges().forEach(function(edge) {\n var handle = dom.element('span', {\n 'class': 'ge-resize-handle ge-resize-' + edge,\n 'data-ge-edge': edge,\n });\n handle.addEventListener('pointerdown', startResizeDrag);\n col.appendChild(handle);\n });\n });\n }\n\n /** Which edges carry a handle: 'e', 'w', or both. */\n function resizeEdges() {\n return String(settings.resize.handles).split(',')\n .map(function(edge) { return edge.trim(); })\n .filter(function(edge) { return edge === 'e' || edge === 'w'; });\n }\n\n /**\n * One resize gesture, from the pointer going down on a handle to it\n * coming up again.\n *\n * The pointer is captured, so a fast drag that leaves the column\n * behind keeps resizing it, and a refused before-resize simply never\n * starts: nothing is written and the column does not move.\n */\n function startResizeDrag(e) {\n var handle = e.currentTarget;\n var col = handle.parentElement;\n var west = handle.getAttribute('data-ge-edge') === 'w';\n var startX = e.pageX;\n var startWidth = dom.outerWidth(col);\n\n e.preventDefault();\n\n if (!resizeStart(col)) { return; }\n\n dom.addClass(col, 'ge-resizing');\n if (e.pointerId !== undefined && handle.setPointerCapture) {\n handle.setPointerCapture(e.pointerId);\n }\n\n function widthAt(move) {\n var delta = move.pageX - startX;\n\n return Math.max(1, startWidth + (west ? -delta : delta));\n }\n\n function onMove(move) {\n col.style.width = widthAt(move) + 'px';\n resizeMove(col, widthAt(move));\n }\n\n function onUp(up) {\n handle.removeEventListener('pointermove', onMove);\n dom.off(handle, 'pointerup pointercancel', onUp);\n dom.removeClass(col, 'ge-resizing');\n resizeStop(col, widthAt(up));\n }\n\n handle.addEventListener('pointermove', onMove);\n dom.on(handle, 'pointerup pointercancel', onUp);\n }\n\n function removeResizable() {\n removeResizeFurniture(canvas);\n }\n\n function removeResizeFurniture(root) {\n dom.all(root, '.ge-resize-handle').forEach(function(handle) { handle.remove(); });\n\n dom.all(root, '.ge-resize-size').forEach(function(readout) { readout.remove(); });\n stripPixelWidths(root);\n }\n\n /**\n * The units a pixel width comes to, snapped to whole ones and held\n * inside the same budget the tools obey. With balance 'next' the\n * column may grow into its neighbour, which is what dragging the\n * divider between two columns looks like it should do.\n */\n function snapUnits(col, pixels) {\n var units = Math.round(pixels / rowContentWidth(col.parentElement) * MAX_COL_SIZE);\n var next = balanceSibling(col);\n var nextSize = next ? currentSize(next) : null;\n\n // Measured when the drag started: the column is the width of the\n // pointer now, which is not what it was\n var resize = resizes.get(col);\n var own = resize ? resize.units : currentUnits(col);\n\n // With a sibling to balance against, the drag may take that\n // column's units but not its last one. Without one, the row is\n // allowed to wrap - that is what balance false means - so the only\n // limit is the column's own budget against its indent.\n // An equal or auto sibling gives way by itself, so it sets no limit\n var room = next && isUnits(nextSize)\n ? own + nextSize - smallest(settings.valid_col_sizes)\n : MAX_COL_SIZE - currentOffset(col);\n\n return Math.min(\n Math.max(units, smallest(settings.valid_col_sizes)),\n Math.max(room, smallest(settings.valid_col_sizes)),\n largest(settings.valid_col_sizes)\n );\n }\n\n /** The column that absorbs the delta, when the host asked for that. */\n function balanceSibling(col) {\n if (settings.resize.balance !== 'next') { return null; }\n\n return dom.nextAll(col, '.column')[0] || null;\n }\n\n function resizeReadout(col, text) {\n var drawer = dom.child(col, '.ge-tools-drawer');\n var readout = drawer ? dom.child(drawer, '.ge-resize-size') : null;\n if (readout) { readout.textContent = text; }\n }\n\n function sizeLabel(units) {\n return (curView === ALL_VIEW ? BREAKPOINTS[0].colPrefix : leadingTier().colPrefix) + units;\n }\n\n /**\n * A canceled before-resize refuses the gesture before it begins, so\n * nothing is written and the column does not move. Under jQuery UI\n * this took a flag on the column and a refusal from every step of the\n * drag, because resizable ignores false from its start handler.\n */\n function resizeStart(col) {\n var from = currentSize(col);\n\n var allowed = operate(function() {\n return emit('before-resize', payloadFor('column', col, {\n source: 'dragdrop',\n from: from,\n to: null, // Not known until the pointer stops\n }));\n });\n\n if (!allowed) { return false; }\n\n var resize = { from: from, units: currentUnits(col) };\n resizes.set(col, resize);\n resizeReadout(col, sizeLabel(resize.units));\n\n return true;\n }\n\n function resizeMove(col, width) {\n resizeReadout(col, sizeLabel(snapUnits(col, width)));\n }\n\n function resizeStop(col, width) {\n var resize = resizes.get(col);\n var units = snapUnits(col, width);\n\n resizes.delete(col);\n resizeReadout(col, '');\n stripPixelWidths(col);\n\n if (!resize) { return; }\n\n // A drag of a couple of pixels lands on the size it started from,\n // and is not a resize - not even of an equal or auto column,\n // which it would otherwise turn into a number\n if (units === resize.units) { return; }\n\n var plan = planSize(col, units);\n if (!plan) { return; }\n\n operate(function() {\n writeSize(col, plan);\n balanceAfterResize(col, units - resize.units);\n refreshUtilities(col);\n\n emit('after-resize', payloadFor('column', col, withCleared({\n source: 'dragdrop',\n from: resize.from,\n to: plan.size,\n }, plan.cleared)));\n });\n }\n\n /**\n * The column after takes what the resized one gave or took, unless it\n * is equal or auto: those take what is left by themselves. It is part\n * of the same gesture, so it is not announced separately.\n */\n function balanceAfterResize(col, delta) {\n var next = balanceSibling(col);\n if (!next || !delta) { return; }\n\n var size = currentSize(next);\n if (!isUnits(size)) { return; }\n\n var plan = planSize(next, size - delta);\n if (plan) {\n writeSize(next, plan);\n refreshUtilities(next);\n }\n }\n\n /**\n * Undo every list `sortable()` made, and only those.\n *\n * The registry is what makes that exact: deinit() is a public method,\n * so it can be called twice, and a list the host made sortable itself\n * is none of the editor's business.\n */\n function removeSortable() {\n sortables.forEach(function(sortableInstance) { sortableInstance.destroy(); });\n\n sortables = [];\n }\n\n function createRow() {\n return dom.element('div', { 'class': 'row' });\n }\n\n /**\n * Put a freshly created node where the caller asked for it, through\n * the add events, and bring the canvas up to date so the new markup\n * gets its controls. With no placement option the node stays\n * detached, and placing it and calling reset() is the host's job\n * (spec 1.2).\n *\n * The place is an element, or the first one a selector matches.\n * Returns the node, or null when a handler canceled the add. A call\n * made from inside an event handler is queued, and then returns the\n * node without knowing yet whether the add will be canceled.\n */\n function place(node, kind, options) {\n var placement = null;\n\n PLACEMENTS.forEach(function(name) {\n if (placement === null && options && options[name] !== undefined) {\n placement = name;\n }\n });\n\n if (placement === null) { return node; }\n\n var target = nodeFrom(options[placement]);\n if (!target) {\n warn(kind + ': ' + placement + ' matches no element; the ' + kind + ' is left detached');\n return node;\n }\n\n var parent = (placement === 'appendTo' || placement === 'prependTo')\n ? target\n : target.parentElement;\n\n var add = function() {\n return addNode(kind, node, function() {\n if (placement === 'appendTo') {\n target.appendChild(node);\n } else if (placement === 'prependTo') {\n target.insertBefore(node, target.firstChild);\n } else if (placement === 'insertBefore') {\n target.parentNode.insertBefore(node, target);\n } else {\n dom.insertAfter(node, target);\n }\n }, { parent: parent, source: options.source || 'api' });\n };\n\n if (operationDepth > 0) {\n defer(add);\n return node;\n }\n\n return add();\n }\n\n /**\n * A row, optionally with columns in it: createRow([8, 4]).\n */\n function apiCreateRow(layout, options) {\n var row = createRow();\n\n if (layout !== undefined && !Array.isArray(layout) && !(layout && layout.row_cols)) {\n warn('createRow: the layout is an array of column sizes, as in [8, 4], or ' +\n '{ row_cols, columns }. Making an empty row instead.');\n layout = [];\n }\n\n if (layout && !Array.isArray(layout)) { row = rowFromLayoutValue(layout); }\n\n (Array.isArray(layout) ? layout : []).forEach(function(size) {\n row.appendChild(createColumn(size));\n });\n\n return place(row, 'row', options);\n }\n\n /**\n * A column of `size` units, optionally holding `options.content`.\n */\n function apiCreateColumn(size, options) {\n options = options || {};\n\n // Going into a row with row-cols, no size is a size: the row's share\n var into = nodeFrom(options.appendTo || options.prependTo || null);\n\n if (size === undefined && into && rowColsSource(into, leadingTier())) {\n size = null;\n } else if (!isUnits(size) && FLEX_SIZES.indexOf(size) === -1) {\n warn('createColumn: no column size given, using ' + MAX_COL_SIZE);\n size = MAX_COL_SIZE;\n }\n\n var column = createColumn(size, options.offset);\n if (options.content !== undefined) {\n column.appendChild(contentFor(options.content));\n }\n\n return place(column, 'column', options);\n }\n\n /**\n * A container of the given type, with its panes already in it.\n */\n function apiCreateContainer(type, options) {\n options = options || {};\n\n var definition = CONTAINERS[type];\n if (!definition) {\n warn('createContainer: no such container type \"' + type + '\"');\n return null;\n }\n\n return place(definition.create(options), type, options);\n }\n\n /** A pane appended to a container, through the add events. */\n function addPaneTo(container, type, options) {\n container = nodeFrom(container);\n options = options || {};\n\n var definition = CONTAINERS[containerTypeOf(container)];\n\n if (!definition || containerTypeOf(container) !== type) {\n warn('this is not a ' + type + ' container');\n return null;\n }\n\n var pane = definition.addPane(container, options);\n if (!pane) { return null; }\n\n return addNode(definition.paneKind, pane, function() {}, {\n parent: container,\n source: 'api',\n container: container,\n });\n }\n\n /** A pane appended to a container of any type that has panes. */\n function apiAddPane(container, options) {\n container = nodeFrom(container);\n\n var type = containerTypeOf(container);\n if (!CONTAINERS[type] || !CONTAINERS[type].addPane) {\n warn('addPane: this is not a container with panes');\n return null;\n }\n\n return addPaneTo(container, type, options);\n }\n\n /**\n * A shallow frozen copy of the settings for the instance, so a host\n * can read what the editor is running with without changing it\n * behind the editor's back. Arrays are copied; the objects inside them\n * are the host's own and stay shared.\n */\n function settingsCopy() {\n var copy = {};\n\n Object.keys(settings).forEach(function(key) {\n var value = settings[key];\n copy[key] = Array.isArray(value) ? value.slice() : value;\n });\n\n return Object.freeze(copy);\n }\n\n /**\n * A column sized for the current view: its tier, or the base class in\n * the all view. `offset` indents it, within the same 12 unit budget.\n */\n function createColumn(size, offset) {\n // Empty: what goes in it is the next decision, and the tools of\n // the column and the toolbar are where it is made\n var column = dom.element('div', { 'class': 'column' });\n\n // The tier being edited, or the base class in the all view\n var tier = tiersFor(curView)[0];\n var wanted = clamp({ size: size, offset: offset || 0, leading: 'offset' });\n\n setSize(column, tier, wanted.size === null ? size : wanted.size);\n setOffset(column, tier, wanted.offset);\n\n return column;\n }\n\n /**\n * Run custom content filter on init and deinit. A filter is a\n * function, or the name of one on window, and gets the canvas and\n * whether this is init.\n */\n function runFilter(isInit, root) {\n if (!settings.custom_filter || !settings.custom_filter.length) { return; }\n\n var filters = typeof settings.custom_filter === 'string' || typeof settings.custom_filter === 'function'\n ? [settings.custom_filter]\n : settings.custom_filter;\n\n Array.prototype.forEach.call(filters, function(func) {\n if (typeof func == 'string') {\n func = window[func];\n }\n\n func(root || canvas, isInit);\n });\n }\n\n /**\n * What a text is never made of: rows, containers, and whatever a\n * feature plugin says - the elements plugin's elements. Each is a\n * block of the column's, beside the texts.\n */\n function textCutter() {\n var cuts = ['.row', '[data-ge-container]'];\n\n Object.keys(FEATURES).forEach(function(name) {\n var feature = FEATURES[name];\n var cut = typeof feature.cuts === 'function' ? feature.cuts() : feature.cuts;\n if (cut) { cuts.push(cut); }\n });\n\n return cuts.join(', ');\n }\n\n /**\n * Take the blocks out of the text.\n *\n * Up to 5.x an element lived inside a content area, among the text\n * a rich text editor edited. From 6.0 it is a block of its own, so a\n * content area with one inside - markup 5.x saved - is cut there: the\n * text before stays in the content area, the element goes into the\n * column after it, and the text after goes into a new content area of\n * the same type. Only a content area's own children cut it, which is\n * where 5.x recognized elements; one inside a paragraph is text, as\n * it was. A part with nothing but whitespace is dropped, and the first\n * part that has something keeps the content area, id and classes and\n * all.\n *\n * On every init, and a no-op on markup 6.0 made: nothing to cut. A\n * content area its editor is open on is left for the next init.\n */\n function splitTexts(cutter) {\n dom.all(canvas, '.column > .ge-content, .column > .ge-text-block > .ge-content').forEach(function(area) {\n if (dom.hasClass(area, 'ge-rte-active') || !dom.children(area, cutter).length) { return; }\n\n var type = area.getAttribute('data-ge-content-type');\n var anchor = dom.hasClass(area.parentElement, 'ge-text-block') ? area.parentElement : area;\n var pieces = [];\n var run = [];\n\n Array.prototype.slice.call(area.childNodes).forEach(function(node) {\n if (node.nodeType === 1 && node.matches(cutter)) {\n pieces.push({ text: run }, { block: node });\n run = [];\n } else {\n run.push(node);\n }\n });\n pieces.push({ text: run });\n\n while (area.firstChild) { area.removeChild(area.firstChild); }\n\n var kept = false;\n var last = anchor;\n\n pieces.forEach(function(piece) {\n var placed;\n\n if (piece.block) {\n placed = piece.block;\n } else if (!hasContent(piece.text)) {\n return;\n } else if (kept) {\n // Of the same type, or of none if it had none\n placed = createDefaultContentWrapper(type);\n piece.text.forEach(function(node) { placed.appendChild(node); });\n } else {\n // The content area itself, moved along if an\n // element came before the first text\n piece.text.forEach(function(node) { area.appendChild(node); });\n placed = anchor;\n kept = true;\n }\n\n if (placed !== last) { dom.insertAfter(placed, last); }\n last = placed;\n });\n\n if (!kept) { anchor.remove(); }\n });\n }\n\n /** Whether a run of nodes has anything in it but whitespace. */\n function hasContent(nodes) {\n return nodes.some(function(node) {\n return node.nodeType === 1 || (node.nodeType === 3 && /\\S/.test(node.nodeValue));\n });\n }\n\n /**\n * Wrap column content in <div class=\"ge-content\"> where neccesary\n */\n function wrapContent(cutter) {\n dom.all(canvas, '.column').forEach(function(col) {\n var contents = [];\n\n dom.children(col).forEach(function(child) {\n // The editor's own furniture is not content and not a\n // boundary either. The resize handle used to be treated as\n // content and wrapped into a content area of its own on\n // the next init.\n if (dom.is(child, '.ge-tools-drawer, .ge-resize-handle')) { return; }\n\n // A container, or an element, sits in the column beside\n // the content areas, not inside one, so it ends a run of\n // loose content rather than joining it\n if (dom.is(child, '.ge-content, .ge-text-block') || child.matches(cutter)) {\n contents = doWrap(contents);\n } else {\n contents.push(child);\n }\n });\n\n doWrap(contents);\n });\n }\n\n /**\n * Wrap a run of loose column content in a content area of no type -\n * the host's plain content - and hand back\n * an empty run: the caller has to forget what it just wrapped, or the\n * next boundary wraps the same nodes again and leaves the first\n * wrapper behind, empty.\n */\n function doWrap(contents) {\n if (contents.length) {\n var contentArea = dom.insertAfter(createDefaultContentWrapper(), contents[contents.length - 1]);\n contents.forEach(function(node) { contentArea.appendChild(node); });\n }\n\n return [];\n }\n\n /**\n * A content area of a text type, or with none the host's plain\n * content: a content area and nothing more.\n */\n function createDefaultContentWrapper(type) {\n var contentArea = dom.element('div', { 'class': 'ge-content' });\n\n if (type) {\n dom.addClass(contentArea, 'ge-content-type-' + type);\n contentArea.setAttribute('data-ge-content-type', type);\n }\n\n return contentArea;\n }\n\n /* --------------------------------------------------------------\n * Content blocks: a content area as a block of its own, with a drawer.\n *\n * The drawer cannot go inside the content area, as every other\n * block's does: what is inside may be a text editor's, which would\n * make the drawer editable text, copy it into its own document or\n * take it away on an undo. So while editing, each content area in a\n * column sits in a .ge-text-block beside its drawer, and that wrapper\n * is the block the column moves. deinit takes it off again: it is\n * never part of the markup.\n *\n * A content area with no type is the host's plain content, and its\n * drawer is the editor's: move and delete, nothing else. One whose\n * type a plugin declares is that plugin's text, and the plugin gives\n * it its drawer. One whose type nobody declares is a text whose\n * editor is not loaded: a block to move and delete, not to edit.\n * -------------------------------------------------------------- */\n\n function wrapTexts() {\n dom.all(canvas, '.column > .ge-content').forEach(function(area) {\n dom.wrap(area, dom.element('div', { 'class': 'ge-text-block' }));\n });\n\n dom.all(canvas, '.ge-text-block').forEach(function(textBlock) {\n if (dom.child(textBlock, '.ge-tools-drawer')) { return; }\n\n var area = dom.child(textBlock, '.ge-content');\n var type = area ? area.getAttribute('data-ge-content-type') : null;\n\n if (!type) {\n createPlainControls(textBlock);\n } else if (!hasTextOwner(type)) {\n createOrphanControls(textBlock, type);\n }\n });\n }\n\n /** After the drawers are gone, so a wrapper holds its content area and nothing else. */\n function unwrapTexts(root) {\n dom.all(root, '.ge-text-block').forEach(function(textBlock) {\n dom.unwrap(textBlock);\n });\n }\n\n /** The host's plain content: moved and deleted here, edited in the source. */\n function createPlainControls(textBlock) {\n var block = dom.child(textBlock, '.ge-content');\n var drawer = prependDrawer(textBlock, 'ge-tools-drawer ge-text-drawer ge-plain-drawer');\n dom.addClass(textBlock, 'ge-plain-block');\n\n createMoveTool(drawer);\n\n // The tools a feature plugin gives plain content, which is not\n // every plugin's drawerTools: no gear, no utilities, no copy\n Object.keys(FEATURES).forEach(function(name) {\n if (FEATURES[name].plainTools) { FEATURES[name].plainTools(drawer, block); }\n });\n\n createTool(drawer, t('tool.delete_plain'), 'ge-delete-plain', 'bi bi-trash', function() {\n deleteNode('plain', block, t('confirm.delete_plain'), function(removed) {\n dom.slideUp(textBlock, function() {\n textBlock.remove();\n removed();\n });\n });\n });\n }\n\n /**\n * A text whose editor is not loaded: still a block to move and delete,\n * and its drawer says why it cannot be edited.\n */\n function createOrphanControls(textBlock, type) {\n var block = dom.child(textBlock, '.ge-content');\n var drawer = prependDrawer(textBlock, 'ge-tools-drawer ge-text-drawer');\n\n createMoveTool(drawer);\n createTool(drawer, t('text.no_editor', { type: type }), 'ge-text-info ge-text-missing',\n 'bi bi-exclamation-triangle');\n createTool(drawer, t('tool.delete_text'), 'ge-delete-text', 'bi bi-trash', function() {\n deleteNode('text', block, t('confirm.delete_text'), function(removed) {\n dom.slideUp(textBlock, function() {\n textBlock.remove();\n removed();\n });\n });\n });\n }\n\n /**\n * A detached content area holding `content` - html, or a node - as a\n * text of the first type offered, or the host's plain content when no\n * editor is offered.\n */\n function contentFor(content) {\n var offers = textOffers();\n var area = createDefaultContentWrapper(offers.length ? offers[0].type : null);\n\n if (content && content.nodeType) {\n area.appendChild(content);\n } else {\n dom.setHtml(area, content);\n }\n\n return area;\n }\n\n /**\n * Constrain the canvas to the view's preview width and make that\n * tier's classes the effective ones. The all view constrains nothing:\n * every tier is live, which is how the page will really render.\n */\n function switchLayout(view) {\n curView = view;\n\n VIEW_KEYS.forEach(function(key) {\n dom.toggleClass(canvas, 'ge-layout-' + key, key === view);\n });\n dom.one(layoutDropdown, 'button').textContent = t(labelKeyFor(view));\n }\n\n /** The view key a caller asked for, or null. */\n function viewKey(view) {\n return VIEW_KEYS.indexOf(view) === -1 ? null : view;\n }\n\n function changeView(view) {\n var key = viewKey(view);\n\n if (key === null) {\n warn('changeView(' + JSON.stringify(view) + '): no such layout mode');\n return;\n }\n\n var from = curView;\n switchLayout(key);\n\n if (key === from) { return; }\n\n settingsScope().forEach(function(scope) {\n dom.all(scope, '.ge-utilities').forEach(function(section) { renderUtilities(section); });\n });\n renderPluginFields(null);\n refreshPreviews(canvas);\n plugins('onViewChange', key);\n emit('view-change', { canvas: canvas, breakpoint: key, from: from, to: key });\n }\n\n function getView() {\n return curView;\n }\n\n /** A method a feature plugin contributes, or a warning that the plugin is not loaded. */\n function featureMethod(name, plugin, file) {\n return function() {\n if (!featureMethods[name]) {\n warnOnceHere('plugin:' + plugin, name + ' needs the ' + plugin + ' plugin: ' +\n 'include dist/plugins/grideditor.' + file + '.js after the editor');\n return null;\n }\n\n return featureMethods[name].apply(null, arguments);\n };\n }\n\n /**\n * The instance's own methods: the documented API. init and reset are\n * deferred when a handler calls them, so an operation in flight\n * finishes before the canvas is rebuilt. The ones that do something,\n * rather than answer something, hand back the instance, to chain.\n */\n function apiSetActiveTarget(value) {\n if (!settings.active_target) {\n warnOnceHere('active_target', 'setActiveTarget needs the active_target setting: without it, it does nothing');\n return;\n }\n if (value === null || value === undefined) { changeTarget(null); return; }\n\n var node = nodeFrom(value);\n if (!isTarget(node)) {\n var named = typeof value === 'string' ? value : (node ? '<' + node.tagName.toLowerCase() + '>' : String(value));\n warn('setActiveTarget: ' + named + ' is not a column or a region of the canvas');\n return;\n }\n\n changeTarget(node);\n }\n\n function apiSetSelected(value) {\n if (panelMode() !== 'sidebar') {\n warnOnceHere('sidebar-api', 'setSelected needs settings_panel \"sidebar\": without it, it does nothing');\n return;\n }\n if (value === null || value === undefined) { changeSelection(null); return; }\n\n var node = nodeFrom(value);\n if (!node || node === canvas || !canvas.contains(node) || !detailsFor.has(node)) {\n var named = typeof value === 'string' ? value : (node ? '<' + node.tagName.toLowerCase() + '>' : String(value));\n warn('setSelected: ' + named + ' is not a node of the canvas with settings');\n return;\n }\n\n changeSelection(node);\n }\n\n var own = {\n getHtml: getHtml,\n getPlainHtml: getPlainHtml,\n init: function() { defer(init); },\n reset: function() { defer(reset); },\n deinit: deinit,\n destroy: destroy,\n changeView: changeView,\n getView: getView,\n createRow: apiCreateRow,\n createColumn: apiCreateColumn,\n createText: function(type, options) {\n if (!featureMethods.createText) {\n warnOnceHere('plugin:text', 'createText needs a text editor plugin: include ' +\n 'dist/plugins/grideditor.tinymce.js, or another editor\\'s, after the editor');\n return null;\n }\n\n return featureMethods.createText(type, options);\n },\n createElement: featureMethod('createElement', 'elements', 'elements'),\n createSection: featureMethod('createSection', 'sections', 'sections'),\n createContainer: apiCreateContainer,\n addTab: function(container, options) { return addPaneTo(container, 'tabs', options); },\n addAccordionItem: function(container, options) {\n return addPaneTo(container, 'accordion', options);\n },\n addPane: apiAddPane,\n setLocale: setLocale,\n getUtility: getUtility,\n setUtility: setUtility,\n getActiveTarget: function() { return settings.active_target ? activeTarget : null; },\n setActiveTarget: apiSetActiveTarget,\n getSelected: function() { return panelMode() === 'sidebar' ? selected : null; },\n setSelected: apiSetSelected,\n };\n\n Object.keys(own).forEach(function(name) {\n var value = !!(METHODS[name] && METHODS[name].value);\n\n instance[name] = function() {\n if (destroyed) {\n warnOnceHere('destroyed:' + name, t('warning.destroyed', { method: name }));\n if (name === 'getHtml') { return canvas.innerHTML; }\n if (name === 'getPlainHtml') { return plainHtml(canvas.innerHTML); }\n return value ? null : instance;\n }\n\n var result = own[name].apply(instance, arguments);\n return value ? result : instance;\n };\n });\n\n instance.canvas = canvas;\n instance.settings = settingsCopy();\n\n instances.set(canvas, instance);\n\n loadPlugins();\n // Again, with what the plugins filled in: the text editors'\n // content_types when the host gave none\n instance.settings = settingsCopy();\n\n // A feature plugin's methods that are not the editor's own documented\n // ones - the autosave plugin's - are the instance's too, while the\n // plugin is there\n Object.keys(featureMethods).forEach(function(name) {\n if (Object.prototype.hasOwnProperty.call(own, name) || name in instance) { return; }\n\n instance[name] = function() {\n if (destroyed) {\n warnOnceHere('destroyed:' + name, t('warning.destroyed', { method: name }));\n return null;\n }\n\n return featureMethods[name].apply(null, arguments);\n };\n });\n setup();\n init();\n\n GridEditor._created.forEach(function(hook) { hook(instance); });\n}\n\n/**\n * What a module that builds on the editor - the jQuery adapter - is told:\n * each editor as it is made. Not the plugin contract; a plugin is handed\n * the editor through its factory.\n */\nGridEditor._created = [];\n\n/**\n * Container plugins: tabs, accordions, popups, carousels, cards, and whatever a host writes.\n *\n * A plugin is a factory registered under the type it builds, called once per\n * editor with the handle described in docs/plugins.md. Loading its file is\n * what makes the type available; the `plugins` setting narrows that list.\n *\n * GridEditor.containers.gallery = function(ge) {\n * return { labelKey: ..., create: ..., mark: ..., unmark: ... };\n * };\n */\nGridEditor.containers = {};\n\n/**\n * Feature plugins: a piece of the editor that is not a container type, in a\n * file of its own. Element level controls are one. Same bargain as a\n * container plugin - a factory under its name, called once per editor with\n * the handle in docs/plugins.md - and the same `plugins` setting decides\n * which of the loaded ones are used.\n */\nGridEditor.features = {};\n\n/**\n * Utility plugins: Bootstrap's responsive utility classes - order-md-2,\n * d-lg-none - edited per breakpoint. A plugin declares families of classes\n * and the editor reads them, writes them, puts them in the settings panel and\n * previews them in each view. Same factory, same `plugins` setting.\n *\n * GridEditor.utilities.order = function(ge) {\n * return { families: [{ name: 'order', prefix: 'order', values: [...] }] };\n * };\n */\nGridEditor.utilities = {};\n\n/**\n * The text editors, by the content type each edits: what the text plugins\n * (tinymce, ckeditor, summernote, a host's own) register, and the text\n * feature, src/js/text/grideditor.text.js, reads.\n */\nGridEditor.texts = {};\n\n/** Translator for the plugins, which get settings and no instance. */\nGridEditor.t = translate;\n\n/** getPlainHtml for html that is not on a canvas, for the jQuery adapter. Not the public API. */\nGridEditor._plainHtml = plainHtml;\n\n/**\n * SortableJS and Bootstrap's javascript, for a page that imports them as\n * modules and so has no window.Sortable or window.bootstrap. Looked up\n * before the globals; only Bootstrap's Modal is used.\n */\nGridEditor.Sortable = null;\nGridEditor.bootstrap = null;\n\n/** The version of the build, filled in by build/build.js. */\nGridEditor.version = typeof __GRIDEDITOR_VERSION__ === 'undefined' ? 'dev' : __GRIDEDITOR_VERSION__;\n\n/**\n * Locale registry: code -> { key: string }.\n *\n * English is built in rather than shipped as a file, because it is where every\n * lookup ends: a page that loads no locale file still has a complete UI.\n * Removing a key from it is a breaking change. Locale files register\n * themselves here, see src/js/locales/.\n *\n * Every key is listed in docs/locale-keys.md, which test/locales.js holds to\n * this catalogue in both directions.\n */\nGridEditor.locales = {\n en: {\n 'tool.move': 'Move',\n 'tool.settings': 'Settings',\n 'tool.add_row': 'Add row',\n 'tool.delete_text': 'Remove text',\n 'tool.delete_plain': 'Remove content',\n 'tool.convert_type': 'Edit as {editor} text',\n 'text.no_editor': 'No text editor \"{type}\" is loaded: this text can be moved and deleted, not edited',\n 'tool.add_column': 'Add column\\n(hold to choose the width)',\n 'tool.column_size': '{size} of 12',\n 'tool.column_equal': 'Equal: shares what the row has left',\n 'tool.column_auto': 'Auto: as wide as its content',\n 'tool.delete_row': 'Remove row',\n 'tool.delete_column': 'Remove col',\n 'tool.delete_container': 'Remove container',\n 'tool.delete_pane': 'Remove pane',\n 'tool.rename': 'Double click to rename',\n 'tool.column_narrower': 'Make column narrower\\n(hold shift for min)',\n 'tool.column_wider': 'Make column wider\\n(hold shift for max)',\n 'tool.indent_decrease': 'Decrease indent\\n(hold shift for none)',\n 'tool.indent_increase': 'Increase indent\\n(hold shift for max)',\n 'tool.edit_source': 'Edit Source Code',\n 'tool.preview': 'Preview',\n 'tool.more': 'More',\n 'group.rows': 'Rows',\n 'group.content': 'Content',\n 'group.elements': 'Elements',\n 'group.select': 'Add',\n 'panel.title': '{kind} settings',\n 'panel.close': 'Close',\n 'panel.done': 'Done',\n 'panel.sidebar_title': 'Settings',\n 'panel.sidebar_empty': 'Click an element to see its settings',\n 'panel.collapse': 'Hide settings',\n 'panel.expand': 'Show settings',\n 'panel.id': 'Id',\n 'panel.classes': 'Classes',\n 'panel.section_general': 'Id and classes',\n 'panel.kind_row': 'Row',\n 'panel.kind_column': 'Column',\n 'panel.kind_element': 'Element',\n 'panel.kind_section': 'Section',\n 'panel.kind_tab': 'Tab',\n 'panel.kind_accordion_item': 'Accordion item',\n 'tool.id_placeholder': 'id',\n 'tool.id_title': 'Set a unique identifier',\n 'tool.classes_placeholder': 'classes',\n 'tool.classes_title': 'Css classes, separated by spaces',\n 'tool.toggle_class': 'Toggle \"{label}\" styling',\n 'row.add': 'Add row {layout}',\n 'row.add_row_cols': 'Add a row of {columns} columns, {counts} per row',\n 'confirm.title': 'Confirm',\n 'confirm.ok': 'Delete',\n 'confirm.cancel': 'Cancel',\n 'confirm.delete_row': 'Delete row?',\n 'confirm.delete_column': 'Delete column?',\n 'confirm.delete_text': 'Delete this text?',\n 'confirm.delete_plain': 'Delete this content?',\n 'confirm.delete_container': 'Delete this container and everything in it?',\n 'view.all': 'All sizes',\n 'view.xs': 'Phone',\n 'view.sm': 'Tablet',\n 'view.md': 'Small desktop',\n 'view.lg': 'Desktop',\n 'view.xl': 'Large desktop',\n 'view.xxl': 'Widescreen',\n 'utility.section': 'Responsive: {view}',\n 'utility.col_width': 'Width',\n 'utility.col_equal': 'Equal',\n 'utility.col_auto': 'Auto',\n 'utility.col_from_row': 'From the row: {count}',\n 'utility.row_cols': 'Columns per row',\n 'badge.row_cols': '{count} per row',\n 'badge.row_cols_auto': 'As wide as their content',\n 'utility.default': 'Default',\n 'utility.inherit': 'Inherit: {value} (from {breakpoint})',\n 'utility.varies': 'Changes at {breakpoints}; choosing here replaces that',\n 'error.sortable_missing': 'SortableJS not available! Make sure you loaded the Sortable js file; dragging is off without it.',\n 'warning.already_editing': 'This element already has an editor: that one is handed back, with the options it was made with.',\n 'warning.destroyed': '{method}() was called on an editor that has been destroyed, and does nothing.',\n 'warning.duplicate_build': 'grideditor.js was loaded twice: the first GridEditor is kept.',\n 'warning.adapter_no_jquery': 'grideditor.jquery.js needs jQuery 4, and there is no jQuery on the page: the jQuery API is not there.',\n 'error.tinymce_missing': 'tinyMCE not available! Make sure you loaded the tinyMCE js file.',\n 'error.ckeditor_missing': 'CKEditor 5 not available! Make sure you loaded its ckeditor5.umd.js file.',\n 'error.summernote_missing': 'Summernote not available! Make sure you loaded jQuery and the Summernote js file.',\n },\n};\n\nexport { GridEditor };\nexport default GridEditor;\n", "/**\n * The classic script's entry: the editor as window.GridEditor, for a page\n * that loads it with a <script> tag and its plugins after it.\n *\n * Loaded twice, the first copy is kept: its plugins registered on it, and\n * the editors on the page are its.\n */\nimport { GridEditor } from './grideditor.js';\n\nif (window.GridEditor) {\n if (window.console && window.console.warn) {\n window.console.warn('grid-editor: ' + GridEditor.t({ locale: 'en' }, 'warning.duplicate_build'));\n }\n} else {\n window.GridEditor = GridEditor;\n}\n"],
|
|
5
|
+
"mappings": "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",
|
|
6
|
+
"names": ["all", "root", "selector", "one", "selfAndAll", "found", "children", "node", "each", "child", "closest", "stopAt", "is", "attached", "nextAll", "next", "parentsUntil", "stop", "parent", "parse", "html", "template", "create", "nodes", "i", "element", "tag", "attributes", "text", "name", "value", "setHtml", "addClass", "names", "split", "removeClass", "toggleClass", "state", "hasClass", "dropEmptyClass", "dropEmptyStyle", "attr", "css", "styles", "property", "UNITLESS", "defaultDisplays", "defaultDisplay", "probe", "show", "hide", "toggle", "visible", "outerWidth", "outerHeight", "contentHeight", "style", "offset", "box", "insertAfter", "node", "reference", "unwrap", "parent", "wrap", "wrapper", "delegate", "root", "types", "selector", "handler", "options", "listener", "event", "match", "closest", "split", "type", "on", "target", "off", "DEFAULT_DURATION", "animateAway", "node", "frames", "duration", "done", "finish", "hide", "visible", "animation", "called", "once", "slideUp", "style", "shrinkAway", "node", "duration", "done", "width", "animateAway", "style", "from", "to", "METHODS", "PLACEMENTS", "BREAKPOINTS", "ALL_VIEW", "ALL_VIEW_LABEL_KEY", "VIEW_KEYS", "tier", "MAX_COL_SIZE", "MAX_COL_OFFSET", "FLEX_SIZES", "ROW_COLS_VALUES", "rowColsClass", "value", "isUnits", "size", "sizeClass", "breakpoint", "key", "i", "tiersFor", "view", "labelKeyFor", "NESTED_SETTINGS", "warned", "editorCounter", "instances", "sidebarHolder", "EDITOR_CONTROLS", "translate", "settings", "params", "locales", "GridEditor", "locale", "overrides", "string", "warnOnce", "placeholder", "name", "hasString", "warn", "message", "english", "targetElement", "target", "found", "nodeFrom", "node", "sortableLibrary", "modalLibrary", "bootstrap", "plainHtml", "html", "root", "emptied", "all", "marked", "attribute", "classes", "kept", "div", "unwrap", "options", "element", "existing", "doubleWarned", "build", "instance", "baseElem", "optionsOrMethod", "canvas", "mainControls", "wrapper", "addRowGroup", "addContainerGroup", "layoutDropdown", "htmlTextArea", "curView", "confirmDialog", "sizePicker", "sourceOpen", "dropMarker", "activeTarget", "toolbarLifetime", "closeOverflowMenu", "refitToolbar", "addButtons", "shownToolbar", "toolbarGroup", "warnedHere", "sortables", "instanceId", "destroyed", "selected", "sidebarCollapsed", "pluginHandle", "warnOnceHere", "detailsFor", "moves", "resizes", "sectionNodes", "editableLabels", "lifetime", "addClass", "t", "setLocale", "code", "settingsCopy", "removeConfirmModal", "removeSettingsPanels", "removeDialog", "removeMainControls", "createMainControls", "reset", "operationDepth", "deferredWork", "payloadFor", "kind", "extra", "getView", "emit", "payload", "names", "generic", "canceled", "eventName", "event", "callback", "operate", "body", "defer", "work", "addNode", "insert", "addEventName", "init", "askToDelete", "whenConfirmed", "confirmWith", "confirmed", "answer", "Modal", "modal", "confirmModal", "ok", "one", "pendingAnswer", "settle", "toggleClass", "confirmHandlers", "create", "trackModal", "asking", "retireModal", "panel", "gone", "finish", "modalMoving", "hasClass", "on", "deleteNode", "animate", "planSize", "col", "wanted", "clamp", "getEffectiveOffset", "getSize", "refused", "each", "base", "writes", "cleared", "own", "writeSize", "plan", "write", "setSize", "stripPixelWidths", "withCleared", "resizeColumn", "source", "from", "currentSize", "refreshUtilities", "indentColumn", "offset", "everywhere", "currentOffset", "others", "getOffset", "setOffset", "was", "getEffectiveSize", "positionOf", "parent", "children", "child", "kindOf", "fromPlugin", "FEATURES", "feature", "paneKind", "CONTAINERS", "type", "definition", "sourceHtml", "probe", "setHtml", "newRow", "setup", "watchDrawers", "signal", "onScroll", "delegate", "onContentClick", "e", "sidebarMode", "panelMode", "pressed", "clickTarget", "changeSelection", "settingsNodeAt", "openSettingsState", "dialogState", "focus", "is", "isEditing", "changeTarget", "attached", "closest", "reserveSidebarRoom", "region", "targetSelector", "textReady", "block", "plugins", "refreshPreviews", "overflowMenu", "start", "layout", "grouped", "btn", "rowColsText", "addToTarget", "row", "rowFromLayoutValue", "added", "sizes", "rowColsIcon", "icon", "button", "labelButton", "attr", "createRow", "column", "createColumn", "container", "toolbarGroupOf", "endItems", "toolbarOf", "item", "index", "featureButton", "changeView", "btnGroup", "htmlButton", "closeSource", "openSource", "previewButton", "endPreview", "removeClass", "end", "createGroupTabs", "createOverflowMenu", "makeToolbarDraggable", "CORE_GROUPS", "group", "entry", "tabs", "stash", "tab", "groupLabel", "showGroup", "chosen", "first", "shownAddButtons", "items", "refreshToolbar", "previewing", "more", "toggle", "spares", "spareOf", "home", "menuLifetime", "openOverflow", "fit", "pending", "observer", "open", "homes", "into", "label", "iconClass", "colour", "made", "placed", "inRowOfItsOwn", "toolbarDrags", "buttons", "startToolbarDrag", "startX", "startY", "helper", "far", "move", "onMove", "css", "showDropMarker", "onUp", "up", "off", "hideDropMarker", "swallow", "click", "where", "dropPlaceAt", "insertFromToolbar", "pageX", "pageY", "x", "y", "under", "pluginHooks", "before", "blockSelector", "box", "insertFeatureFromToolbar", "acceptsBlock", "ancestors", "parentsUntil", "top", "rowFromLayout", "widthFamily", "values", "units", "parseSize", "winner", "rowColsWinner", "rowColsLabel", "counts", "widest", "scrollTop", "contentHeight", "outerWidth", "closeSizePicker", "visible", "offers", "textOffers", "convertPlain", "openConvertPicker", "offer", "textBlock", "drawer", "openPicker", "anchor", "choices", "className", "hover", "choice", "withdrawOnLeave", "textTypes", "owners", "entries", "hasTextOwner", "deinit", "show", "hide", "isTarget", "closeSettings", "closeDialog", "runFilter", "addAllColClasses", "cutter", "textCutter", "splitTexts", "wrapContent", "wrapTexts", "createRowControls", "createColControls", "markContainers", "makeSortable", "makeResizable", "switchLayout", "showSidebar", "hideSidebar", "removeDrawers", "pluginFields", "unwrapTexts", "clearPreviews", "clearRowCols", "unmarkContainers", "removeSortable", "removeResizable", "pluginsWithoutCleanMarkup", "UTILITIES", "registry", "plugin", "marks", "copyCanvas", "copy", "toLive", "toCopy", "live", "copied", "a", "b", "snapshotHtml", "getHtml", "missing", "dropEmptyClass", "marker", "unmarkContainerClasses", "sortableInstance", "list", "removeResizeFurniture", "nodeHtml", "getPlainHtml", "destroy", "loadPlugins", "api", "pluginApi", "registerFamily", "rowColsFamily", "featureWanted", "factory", "family", "methods", "method", "featureMethods", "hook", "argument", "containerId", "defaultRegion", "createTool", "createMoveTool", "addSettingsTool", "place", "createPaneControls", "makeLabelEditable", "labelIn", "unwrapLabels", "suspendToggles", "resumeToggles", "getUtility", "setUtility", "utilityField", "bareStyle", "hostStyle", "setHostStyle", "openDialog", "attachPicker", "detailsOf", "drawerOf", "FAMILIES", "UTILITY_NODES", "PREVIEW_ATTR", "utilitiesOpen", "pluginName", "utility", "familyNamed", "appliesTo", "familiesFor", "utilityClass", "ownUtility", "inheritedUtility", "effectiveUtility", "inherited", "utilityTiers", "writeUtility", "candidate", "readUtility", "planUtility", "viewKey", "property", "original", "details", "hostClasses", "section", "renderUtilities", "renderPluginFields", "utilityNodes", "scope", "selfAndAll", "previewTier", "markRowCols", "styles", "rowColsPreview", "applyPreview", "style", "error", "dropEmptyStyle", "hostDeclaration", "scratch", "declaration", "priority", "check", "previewed", "createUtilitiesSection", "fields", "createField", "settingsScope", "field", "select", "renderField", "fieldNode", "blank", "note", "varies", "labelOf", "custom", "noteNode", "containerCounter", "containerTypeOf", "createContainerControls", "prependDrawer", "hostTools", "tools", "hostTool", "removed", "slideUp", "pane", "confirmText", "remove", "TOGGLE_ATTRIBUTES", "addColumnTo", "attachSizePicker", "tool", "openSizePicker", "timer", "cancel", "room", "spare", "leadingTier", "sizeTitle", "rowColsSource", "smallest", "stepThrough", "currentUnits", "widestFor", "deepestFor", "shrinkAway", "rowContentWidth", "direction", "best", "largest", "FITTED_DRAWERS", "due", "frame", "schedule", "flush", "drawers", "drawerResizes", "fitDrawer", "mutations", "records", "record", "expanded", "drawerOverflows", "limit", "rects", "title", "eventHandlers", "isEditorClass", "setHostClasses", "presets", "createDetails", "toggleSettings", "cssClasses", "detailsDiv", "sectionTitle", "general", "holder", "id", "classGroup", "rowClass", "pluginSections", "utilities", "text", "mode", "sections", "kindLabel", "PANEL_MODES", "settingsPanels", "modalState", "sidebarShown", "gear", "same", "openSettings", "settingsPanel", "listening", "narrow", "placePopover", "showModal", "hideModal", "returnPanel", "closeButton", "sidebarToggle", "unshowSidebar", "removeBackdrop", "SIDEBAR_MIN_WIDTH", "sidebarEmpty", "foldSidebar", "collapsed", "applySidebar", "renderSidebar", "unshowDetails", "setSidebarTitle", "shown", "content", "emptyContent", "fromHost", "emptyContentOf", "result", "titleOf", "owner", "gap", "width", "height", "outerHeight", "roomBelow", "roomAbove", "below", "left", "dismissed", "state", "dialogPanel", "dialog", "opener", "paneLabel", "sizedTiers", "hasRowCols", "v", "columnSource", "rowColsUnits", "readUnits", "readEffective", "read", "prefix", "match", "writeUnits", "flex", "ignore", "used", "sibling", "request", "groupName", "accepted", "dragCancelSelector", "sortable", "lists", "Sortable", "wholeDrawer", "soloGroup", "to", "dragged", "sortStart", "sortEnd", "regions", "subject", "moveSubject", "moving", "putBack", "siblings", "resizeEdges", "edge", "handle", "startResizeDrag", "west", "startWidth", "resizeStart", "widthAt", "delta", "resizeMove", "resizeStop", "readout", "snapUnits", "pixels", "next", "balanceSibling", "nextSize", "resize", "nextAll", "resizeReadout", "sizeLabel", "allowed", "balanceAfterResize", "placement", "add", "insertAfter", "apiCreateRow", "apiCreateColumn", "contentFor", "apiCreateContainer", "addPaneTo", "apiAddPane", "isInit", "filters", "func", "cuts", "cut", "area", "pieces", "run", "last", "piece", "hasContent", "createDefaultContentWrapper", "nodes", "contents", "doWrap", "contentArea", "wrap", "createOrphanControls", "createPlainControls", "featureMethod", "file", "apiSetActiveTarget", "named", "apiSetSelected", "GridEditor"]
|
|
7
7
|
}
|