@themarioga/grid-editor 7.2.0 → 8.0.0-beta.2

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.
Files changed (97) hide show
  1. package/CHANGELOG.md +101 -0
  2. package/README.md +96 -30
  3. package/UPGRADING.md +86 -0
  4. package/dist/grideditor.bundle.min.js +3 -3
  5. package/dist/grideditor.css +149 -6
  6. package/dist/grideditor.d.ts +18 -0
  7. package/dist/grideditor.esm.js +257 -48
  8. package/dist/grideditor.jquery.js +0 -13
  9. package/dist/grideditor.jquery.min.js +1 -1
  10. package/dist/grideditor.jquery.min.js.map +3 -3
  11. package/dist/grideditor.js +257 -48
  12. package/dist/grideditor.min.css +1 -1
  13. package/dist/grideditor.min.css.map +1 -1
  14. package/dist/grideditor.min.js +2 -2
  15. package/dist/grideditor.min.js.map +3 -3
  16. package/dist/locales/grideditor.es.esm.js +80 -6
  17. package/dist/locales/grideditor.es.js +80 -6
  18. package/dist/locales/grideditor.es.min.js +1 -1
  19. package/dist/locales/grideditor.es.min.js.map +2 -2
  20. package/dist/plugins/grideditor.accordion.min.js.map +2 -2
  21. package/dist/plugins/grideditor.alignment.esm.js +11 -38
  22. package/dist/plugins/grideditor.alignment.js +11 -38
  23. package/dist/plugins/grideditor.alignment.min.js +1 -1
  24. package/dist/plugins/grideditor.alignment.min.js.map +3 -3
  25. package/dist/plugins/grideditor.card.min.js.map +1 -1
  26. package/dist/plugins/grideditor.ckeditor.esm.js +0 -5
  27. package/dist/plugins/grideditor.ckeditor.js +0 -5
  28. package/dist/plugins/grideditor.ckeditor.min.js +1 -1
  29. package/dist/plugins/grideditor.ckeditor.min.js.map +3 -3
  30. package/dist/plugins/grideditor.clipboard.min.js.map +1 -1
  31. package/dist/plugins/grideditor.codemirror-inline.min.js.map +1 -1
  32. package/dist/plugins/grideditor.codemirror.min.js.map +1 -1
  33. package/dist/plugins/grideditor.elements.min.js.map +2 -2
  34. package/dist/plugins/grideditor.gutters.min.js.map +1 -1
  35. package/dist/plugins/grideditor.order.min.js.map +1 -1
  36. package/dist/plugins/grideditor.popup.min.js.map +1 -1
  37. package/dist/plugins/grideditor.sections.min.js.map +2 -2
  38. package/dist/plugins/grideditor.style.esm.js +1926 -0
  39. package/dist/plugins/grideditor.style.js +1923 -0
  40. package/dist/plugins/grideditor.style.min.js +4 -0
  41. package/dist/plugins/grideditor.style.min.js.map +7 -0
  42. package/dist/plugins/grideditor.summernote.min.js.map +2 -2
  43. package/dist/plugins/grideditor.tabs.min.js.map +2 -2
  44. package/dist/plugins/grideditor.tinymce.esm.js +1 -8
  45. package/dist/plugins/grideditor.tinymce.js +1 -8
  46. package/dist/plugins/grideditor.tinymce.min.js +1 -1
  47. package/dist/plugins/grideditor.tinymce.min.js.map +3 -3
  48. package/docs/events.md +4 -6
  49. package/docs/locale-keys.md +99 -15
  50. package/docs/plugins.md +47 -23
  51. package/example/ckeditor.html +0 -5
  52. package/example/index.html +17 -2
  53. package/example/style.html +163 -0
  54. package/example/utilities.html +21 -16
  55. package/package.json +1 -1
  56. package/src/js/dom.js +1 -2
  57. package/src/js/grideditor.jquery.js +7 -28
  58. package/src/js/grideditor.js +336 -67
  59. package/src/js/locales/grideditor.es.js +80 -6
  60. package/src/js/plugins/grideditor.alignment.js +21 -50
  61. package/src/js/plugins/grideditor.ckeditor.js +10 -23
  62. package/src/js/plugins/grideditor.style.js +185 -0
  63. package/src/js/plugins/grideditor.summernote.js +4 -5
  64. package/src/js/plugins/grideditor.tinymce.js +4 -17
  65. package/src/js/style/accordion.js +168 -0
  66. package/src/js/style/catalog.js +76 -0
  67. package/src/js/style/custom.js +84 -0
  68. package/src/js/style/display.js +229 -0
  69. package/src/js/style/drawerflow.js +118 -0
  70. package/src/js/style/fields.js +382 -0
  71. package/src/js/style/flex.js +156 -0
  72. package/src/js/{plugins/grideditor.float.js → style/float.js} +6 -16
  73. package/src/js/style/options.js +60 -0
  74. package/src/js/style/sections.js +298 -0
  75. package/src/js/{plugins/grideditor.spacing.js → style/spacing.js} +7 -19
  76. package/src/js/style/sticky.js +39 -0
  77. package/src/js/{plugins/grideditor.textalign.js → style/textalign.js} +6 -14
  78. package/src/js/text/grideditor.text.js +1 -1
  79. package/src/less/grideditor.less +151 -10
  80. package/types/grideditor.d.ts +18 -0
  81. package/dist/plugins/grideditor.float.esm.js +0 -34
  82. package/dist/plugins/grideditor.float.js +0 -41
  83. package/dist/plugins/grideditor.float.min.js +0 -1
  84. package/dist/plugins/grideditor.float.min.js.map +0 -7
  85. package/dist/plugins/grideditor.spacing.esm.js +0 -318
  86. package/dist/plugins/grideditor.spacing.js +0 -323
  87. package/dist/plugins/grideditor.spacing.min.js +0 -1
  88. package/dist/plugins/grideditor.spacing.min.js.map +0 -7
  89. package/dist/plugins/grideditor.textalign.esm.js +0 -40
  90. package/dist/plugins/grideditor.textalign.js +0 -47
  91. package/dist/plugins/grideditor.textalign.min.js +0 -1
  92. package/dist/plugins/grideditor.textalign.min.js.map +0 -7
  93. package/dist/plugins/grideditor.visibility.esm.js +0 -158
  94. package/dist/plugins/grideditor.visibility.js +0 -163
  95. package/dist/plugins/grideditor.visibility.min.js +0 -1
  96. package/dist/plugins/grideditor.visibility.min.js.map +0 -7
  97. package/src/js/plugins/grideditor.visibility.js +0 -171
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "version": 3,
3
3
  "sources": ["../../src/js/register.js", "../../src/js/dom.js", "../../src/js/plugins/grideditor.gutters.js"],
4
- "sourcesContent": ["/**\n * What a plugin's or a locale's classic script imports in place of the\n * editor: the GridEditor the page already loaded.\n *\n * The build points `import { GridEditor } from '../grideditor.js'` here for\n * the classic scripts, so each registers on the editor the page has rather\n * than bringing its own. Loaded before the editor there is nothing to\n * register on, and saying so is better than a TypeError three calls later.\n */\nvar GridEditor = window.GridEditor;\n\nif (!GridEditor || typeof GridEditor.get !== 'function') {\n throw new Error('grid-editor: load grideditor.js (or grideditor.bundle.min.js) before its plugins, ' +\n 'its locales and grideditor.jquery.js');\n}\n\nexport { GridEditor };\nexport default GridEditor;\n", "/**\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 the ones 6.x had through jQuery: 400 ms unless the\n * 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 * Gutters for grid-editor.\n *\n * A utility plugin: load this file after the editor and a row's gutters can\n * differ per breakpoint, with Bootstrap's g-{breakpoint}-*, gx-{breakpoint}-*\n * and gy-{breakpoint}-* classes. What it can ask the editor for is the handle\n * its factory is called with, described in docs/plugins.md.\n *\n * <script src=\"dist/grideditor.min.js\"></script>\n * <script src=\"dist/plugins/grideditor.gutters.min.js\"></script>\n *\n * The editor draws its own frame round every column, narrower than any\n * gutter, so a row with gutter classes is drawn with its real gutters instead.\n *\n * utilities.gutters.scale is what 0 to 5 come to, for a page that changed\n * Bootstrap's $spacers.\n */\nimport { GridEditor } from '../grideditor.js';\nimport * as dom from '../dom.js';\n\nObject.assign(GridEditor.locales.en, {\n 'utility.gutters': 'Gutters',\n 'utility.gutters_x': 'Horizontal gutters',\n 'utility.gutters_y': 'Vertical gutters',\n});\n\nvar VALUES = ['0', '1', '2', '3', '4', '5'];\n\n/** Bootstrap's own: $spacers, and what a row's gutters are with no class. */\nvar SCALE = ['0', '.25rem', '.5rem', '1rem', '1.5rem', '3rem'];\nvar DEFAULT_X = '1.5rem';\nvar DEFAULT_Y = '0';\n\nvar INFIXES = ['', 'sm', 'md', 'lg', 'xl', 'xxl'];\nvar CLASS_PATTERN = /(?:^|\\s)g[xy]?-(?:(?:sm|md|lg|xl|xxl)-)?[0-5](?:\\s|$)/;\n\nGridEditor.utilities.gutters = function(ge) {\n\n var options = Object.assign({ scale: SCALE }, ge.settings.utilities.gutters);\n var listening = null; // The after-utility listener, while editing\n\n /**\n * The class of a family that decides a row's gutters at a breakpoint:\n * the widest breakpoint up to it that has one, as { tier, value }.\n */\n function source(row, prefix, tier) {\n var classes = (row.getAttribute('class') || '').split(/\\s+/);\n\n for (var i = tier; i >= 0; i--) {\n for (var value = VALUES.length - 1; value >= 0; value--) {\n var name = prefix + (INFIXES[i] ? '-' + INFIXES[i] : '') + '-' + value;\n if (classes.indexOf(name) !== -1) { return { tier: i, value: value }; }\n }\n }\n\n return null;\n }\n\n /**\n * One axis the way Bootstrap's css settles it. g and gx (or gy) set the\n * same variable, every breakpoint's rules come after the smaller ones',\n * and within a breakpoint the bigger values come later. So the class\n * that wins is the one from the wider breakpoint, then the bigger one -\n * not the more specific family, whatever that would suggest.\n */\n function axis(row, prefix, fallback) {\n var tier = ge.breakpoints.indexOf(ge.view());\n var winner = [source(row, 'g', tier), source(row, prefix, tier)]\n .filter(Boolean)\n .sort(function(a, b) { return b.tier - a.tier || b.value - a.value; })[0];\n\n return winner ? options.scale[winner.value] : fallback;\n }\n\n function preview(axes) {\n return function(value, row) {\n var styles = {};\n\n if (axes.indexOf('x') !== -1) { styles['--bs-gutter-x'] = axis(row, 'gx', DEFAULT_X); }\n if (axes.indexOf('y') !== -1) { styles['--bs-gutter-y'] = axis(row, 'gy', DEFAULT_Y); }\n\n return styles;\n };\n }\n\n /**\n * Choosing g sets both axes, so a gx or gy the same breakpoint had is\n * taken off: left on, the bigger of the two would win, and the field the\n * user just chose would not be what the row shows.\n */\n function afterUtility(e) {\n var payload = e.detail;\n if (payload.family !== 'g') { return; }\n\n ['gx', 'gy'].forEach(function(family) {\n ge.setUtility(payload.node, family, null, { view: payload.breakpoint, source: payload.source });\n });\n }\n\n function mark(scope) {\n dom.selfAndAll(scope, '.row').forEach(function(row) {\n dom.toggleClass(row, 'ge-gutters', CLASS_PATTERN.test(row.getAttribute('class') || ''));\n });\n }\n\n return {\n families: [\n {\n name: 'g',\n prefix: 'g',\n values: VALUES,\n appliesTo: ['row'],\n labelKey: 'utility.gutters',\n preview: preview(['x', 'y']),\n },\n {\n name: 'gx',\n prefix: 'gx',\n values: VALUES,\n appliesTo: ['row'],\n labelKey: 'utility.gutters_x',\n preview: preview(['x']),\n },\n {\n name: 'gy',\n prefix: 'gy',\n values: VALUES,\n appliesTo: ['row'],\n labelKey: 'utility.gutters_y',\n preview: preview(['y']),\n },\n ],\n\n onInit: function() {\n // init runs again whenever a node is added, without a deinit\n // between, so the listener is replaced rather than stacked\n if (listening) { ge.canvas.removeEventListener('grideditor:after-utility', listening); }\n listening = afterUtility;\n ge.canvas.addEventListener('grideditor:after-utility', listening);\n },\n\n onRefresh: mark,\n\n onDeinit: function() {\n if (listening) { ge.canvas.removeEventListener('grideditor:after-utility', listening); }\n listening = null;\n dom.all(ge.canvas, '.ge-gutters').forEach(function(row) { dom.removeClass(row, 'ge-gutters'); });\n },\n };\n};\n"],
4
+ "sourcesContent": ["/**\n * What a plugin's or a locale's classic script imports in place of the\n * editor: the GridEditor the page already loaded.\n *\n * The build points `import { GridEditor } from '../grideditor.js'` here for\n * the classic scripts, so each registers on the editor the page has rather\n * than bringing its own. Loaded before the editor there is nothing to\n * register on, and saying so is better than a TypeError three calls later.\n */\nvar GridEditor = window.GridEditor;\n\nif (!GridEditor || typeof GridEditor.get !== 'function') {\n throw new Error('grid-editor: load grideditor.js (or grideditor.bundle.min.js) before its plugins, ' +\n 'its locales and grideditor.jquery.js');\n}\n\nexport { GridEditor };\nexport default GridEditor;\n", "/**\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 * Gutters for grid-editor.\n *\n * A utility plugin: load this file after the editor and a row's gutters can\n * differ per breakpoint, with Bootstrap's g-{breakpoint}-*, gx-{breakpoint}-*\n * and gy-{breakpoint}-* classes. What it can ask the editor for is the handle\n * its factory is called with, described in docs/plugins.md.\n *\n * <script src=\"dist/grideditor.min.js\"></script>\n * <script src=\"dist/plugins/grideditor.gutters.min.js\"></script>\n *\n * The editor draws its own frame round every column, narrower than any\n * gutter, so a row with gutter classes is drawn with its real gutters instead.\n *\n * utilities.gutters.scale is what 0 to 5 come to, for a page that changed\n * Bootstrap's $spacers.\n */\nimport { GridEditor } from '../grideditor.js';\nimport * as dom from '../dom.js';\n\nObject.assign(GridEditor.locales.en, {\n 'utility.gutters': 'Gutters',\n 'utility.gutters_x': 'Horizontal gutters',\n 'utility.gutters_y': 'Vertical gutters',\n});\n\nvar VALUES = ['0', '1', '2', '3', '4', '5'];\n\n/** Bootstrap's own: $spacers, and what a row's gutters are with no class. */\nvar SCALE = ['0', '.25rem', '.5rem', '1rem', '1.5rem', '3rem'];\nvar DEFAULT_X = '1.5rem';\nvar DEFAULT_Y = '0';\n\nvar INFIXES = ['', 'sm', 'md', 'lg', 'xl', 'xxl'];\nvar CLASS_PATTERN = /(?:^|\\s)g[xy]?-(?:(?:sm|md|lg|xl|xxl)-)?[0-5](?:\\s|$)/;\n\nGridEditor.utilities.gutters = function(ge) {\n\n var options = Object.assign({ scale: SCALE }, ge.settings.utilities.gutters);\n var listening = null; // The after-utility listener, while editing\n\n /**\n * The class of a family that decides a row's gutters at a breakpoint:\n * the widest breakpoint up to it that has one, as { tier, value }.\n */\n function source(row, prefix, tier) {\n var classes = (row.getAttribute('class') || '').split(/\\s+/);\n\n for (var i = tier; i >= 0; i--) {\n for (var value = VALUES.length - 1; value >= 0; value--) {\n var name = prefix + (INFIXES[i] ? '-' + INFIXES[i] : '') + '-' + value;\n if (classes.indexOf(name) !== -1) { return { tier: i, value: value }; }\n }\n }\n\n return null;\n }\n\n /**\n * One axis the way Bootstrap's css settles it. g and gx (or gy) set the\n * same variable, every breakpoint's rules come after the smaller ones',\n * and within a breakpoint the bigger values come later. So the class\n * that wins is the one from the wider breakpoint, then the bigger one -\n * not the more specific family, whatever that would suggest.\n */\n function axis(row, prefix, fallback) {\n var tier = ge.breakpoints.indexOf(ge.view());\n var winner = [source(row, 'g', tier), source(row, prefix, tier)]\n .filter(Boolean)\n .sort(function(a, b) { return b.tier - a.tier || b.value - a.value; })[0];\n\n return winner ? options.scale[winner.value] : fallback;\n }\n\n function preview(axes) {\n return function(value, row) {\n var styles = {};\n\n if (axes.indexOf('x') !== -1) { styles['--bs-gutter-x'] = axis(row, 'gx', DEFAULT_X); }\n if (axes.indexOf('y') !== -1) { styles['--bs-gutter-y'] = axis(row, 'gy', DEFAULT_Y); }\n\n return styles;\n };\n }\n\n /**\n * Choosing g sets both axes, so a gx or gy the same breakpoint had is\n * taken off: left on, the bigger of the two would win, and the field the\n * user just chose would not be what the row shows.\n */\n function afterUtility(e) {\n var payload = e.detail;\n if (payload.family !== 'g') { return; }\n\n ['gx', 'gy'].forEach(function(family) {\n ge.setUtility(payload.node, family, null, { view: payload.breakpoint, source: payload.source });\n });\n }\n\n function mark(scope) {\n dom.selfAndAll(scope, '.row').forEach(function(row) {\n dom.toggleClass(row, 'ge-gutters', CLASS_PATTERN.test(row.getAttribute('class') || ''));\n });\n }\n\n return {\n families: [\n {\n name: 'g',\n prefix: 'g',\n values: VALUES,\n appliesTo: ['row'],\n labelKey: 'utility.gutters',\n preview: preview(['x', 'y']),\n },\n {\n name: 'gx',\n prefix: 'gx',\n values: VALUES,\n appliesTo: ['row'],\n labelKey: 'utility.gutters_x',\n preview: preview(['x']),\n },\n {\n name: 'gy',\n prefix: 'gy',\n values: VALUES,\n appliesTo: ['row'],\n labelKey: 'utility.gutters_y',\n preview: preview(['y']),\n },\n ],\n\n onInit: function() {\n // init runs again whenever a node is added, without a deinit\n // between, so the listener is replaced rather than stacked\n if (listening) { ge.canvas.removeEventListener('grideditor:after-utility', listening); }\n listening = afterUtility;\n ge.canvas.addEventListener('grideditor:after-utility', listening);\n },\n\n onRefresh: mark,\n\n onDeinit: function() {\n if (listening) { ge.canvas.removeEventListener('grideditor:after-utility', listening); }\n listening = null;\n dom.all(ge.canvas, '.ge-gutters').forEach(function(row) { dom.removeClass(row, 'ge-gutters'); });\n },\n };\n};\n"],
5
5
  "mappings": "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",
6
6
  "names": ["GridEditor", "all", "root", "selector", "selfAndAll", "root", "selector", "found", "all", "removeClass", "node", "names", "split", "name", "toggleClass", "state", "split", "names", "GridEditor", "VALUES", "SCALE", "DEFAULT_X", "DEFAULT_Y", "INFIXES", "CLASS_PATTERN", "ge", "options", "listening", "source", "row", "prefix", "tier", "classes", "i", "value", "name", "axis", "fallback", "winner", "b", "preview", "axes", "styles", "afterUtility", "e", "payload", "family", "mark", "scope", "selfAndAll", "toggleClass", "all", "removeClass"]
7
7
  }
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "version": 3,
3
3
  "sources": ["../../src/js/register.js", "../../src/js/dom.js", "../../src/js/plugins/grideditor.order.js"],
4
- "sourcesContent": ["/**\n * What a plugin's or a locale's classic script imports in place of the\n * editor: the GridEditor the page already loaded.\n *\n * The build points `import { GridEditor } from '../grideditor.js'` here for\n * the classic scripts, so each registers on the editor the page has rather\n * than bringing its own. Loaded before the editor there is nothing to\n * register on, and saying so is better than a TypeError three calls later.\n */\nvar GridEditor = window.GridEditor;\n\nif (!GridEditor || typeof GridEditor.get !== 'function') {\n throw new Error('grid-editor: load grideditor.js (or grideditor.bundle.min.js) before its plugins, ' +\n 'its locales and grideditor.jquery.js');\n}\n\nexport { GridEditor };\nexport default GridEditor;\n", "/**\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 the ones 6.x had through jQuery: 400 ms unless the\n * 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 * Column order for grid-editor.\n *\n * A utility plugin: load this file after the editor and a column's place in\n * its row can differ per breakpoint, with Bootstrap's order-{breakpoint}-*\n * classes. What it can ask the editor for is the handle its factory is called\n * with, described in docs/plugins.md.\n *\n * <script src=\"dist/grideditor.min.js\"></script>\n * <script src=\"dist/plugins/grideditor.order.min.js\"></script>\n *\n * Two arrows in each column's drawer move it one place earlier or later in\n * the view being edited, by numbering the row's columns; the markup does not\n * move. Dragging still moves the markup, as it always has.\n *\n * utilities.order.drawer: false leaves the arrows out, and the panel field is\n * the only control.\n */\nimport { GridEditor } from '../grideditor.js';\nimport * as dom from '../dom.js';\n\nObject.assign(GridEditor.locales.en, {\n 'utility.order': 'Order',\n 'utility.order_first': 'First',\n 'utility.order_last': 'Last',\n 'tool.order_earlier': 'Earlier in this view',\n 'tool.order_later': 'Later in this view',\n 'badge.order': 'Order: {value}',\n});\n\nvar VALUES = ['first', '0', '1', '2', '3', '4', '5', 'last'];\n\n/** Where each value puts a column, as Bootstrap's css has it. */\nvar RANK = { first: -1, last: 6 };\n\n/** A column that carries any class of the family, at any breakpoint. */\nvar CLASS_PATTERN = /(?:^|\\s)order-(?:(?:sm|md|lg|xl|xxl)-)?(?:first|last|[0-5])(?:\\s|$)/;\n\nGridEditor.utilities.order = function(ge) {\n\n var options = Object.assign({ drawer: true }, ge.settings.utilities.order);\n var warnedAboutDrag = false;\n var listening = null; // The after-move listener, while editing\n\n function rank(value) {\n if (value === null) { return 0; }\n\n return RANK[value] !== undefined ? RANK[value] : parseInt(value, 10);\n }\n\n function label(value) {\n if (value === 'first') { return ge.t('utility.order_first'); }\n if (value === 'last') { return ge.t('utility.order_last'); }\n\n return value;\n }\n\n /** The columns of a row in the order a view shows them, given what each one's order is. */\n function visualOrder(columns, read) {\n return columns\n .map(function(element, index) {\n return { element: element, index: index, rank: rank(read(element)) };\n })\n .sort(function(a, b) { return a.rank - b.rank || a.index - b.index; })\n .map(function(entry) { return entry.element; });\n }\n\n function sameOrder(a, b) {\n return a.every(function(element, index) { return element === b[index]; });\n }\n\n /**\n * The values that put n columns in n places, or null past eight: that\n * is how many places Bootstrap's order classes have.\n */\n function slots(count) {\n if (count <= 6) { return VALUES.slice(1, 1 + count); }\n if (count === 7) { return VALUES.slice(1); }\n if (count === 8) { return VALUES.slice(); }\n\n return null;\n }\n\n /**\n * Move a column one place earlier or later in the view being edited.\n *\n * The row's columns are numbered in their new order. When that order is\n * the markup's own, the numbers are taken off instead - unless what is\n * left underneath, the breakpoint below, would then order them some other\n * way, and the numbers are what keep them in the markup's order.\n */\n function move(col, direction) {\n var view = ge.view();\n var columns = dom.children(col.parentElement, '.column');\n var shown = visualOrder(columns, function(column) { return ge.getUtility(column, 'order', view); });\n var from = shown.indexOf(col);\n var to = from + direction;\n\n if (to < 0 || to >= shown.length) { return; }\n\n shown.splice(to, 0, shown.splice(from, 1)[0]);\n\n var values = null;\n if (!sameOrder(shown, columns) || !inheritsMarkupOrder(columns, view)) {\n values = slots(shown.length);\n\n if (!values) {\n ge.warn('a row of ' + shown.length + ' columns cannot be reordered with Bootstrap\\'s ' +\n 'order classes, which have eight places');\n return;\n }\n }\n\n ge.operate(function() {\n shown.forEach(function(element, index) {\n ge.setUtility(element, 'order', values ? values[index] : null, { source: 'tool' });\n });\n });\n }\n\n /** Whether taking this view's classes off leaves the columns in the markup's order. */\n function inheritsMarkupOrder(columns, view) {\n var index = ge.breakpoints.indexOf(view);\n if (index <= 0) { return true; }\n\n var below = ge.breakpoints[index - 1];\n\n return sameOrder(visualOrder(columns, function(column) {\n return ge.getUtility(column, 'order', below);\n }), columns);\n }\n\n /** Whether a row's columns are ordered by class, rather than by the markup, in this view. */\n function ordered(row) {\n return dom.children(row, '.column').some(function(element) {\n return ge.getUtility(element, 'order', ge.view()) !== null;\n });\n }\n\n /** The badge: a column ordered by class in this view says where. */\n function mark(scope) {\n dom.selfAndAll(scope, '.column').forEach(function(col) {\n var value = CLASS_PATTERN.test(col.getAttribute('class') || '')\n ? ge.getUtility(col, 'order', ge.view())\n : null;\n\n if (value === null) {\n col.removeAttribute('data-ge-order');\n } else {\n col.setAttribute('data-ge-order', ge.t('badge.order', { value: label(value) }));\n }\n });\n }\n\n /**\n * A column dropped in a row ordered by class lands where the markup puts\n * it, and shows up where its order does, which is worth saying once.\n */\n function afterMove(e) {\n var payload = e.detail;\n if (warnedAboutDrag || payload.kind !== 'column' || !payload.to) { return; }\n if (!ordered(payload.to.parent)) { return; }\n\n warnedAboutDrag = true;\n ge.warn('a column was dropped in a row whose columns carry order classes in this view: ' +\n 'where it shows is set by those classes, not by where it sits in the markup');\n }\n\n return {\n families: [{\n name: 'order',\n prefix: 'order',\n values: VALUES,\n appliesTo: ['column'],\n labelKey: 'utility.order',\n label: label,\n preview: function(value) {\n return { order: rank(value) };\n },\n }],\n\n drawerTools: function(drawer, node, kind) {\n if (!options.drawer || kind !== 'column') { return; }\n\n ge.createTool(drawer, ge.t('tool.order_earlier'), 'ge-order-earlier', 'bi bi-chevron-left', function() {\n move(node, -1);\n });\n ge.createTool(drawer, ge.t('tool.order_later'), 'ge-order-later', 'bi bi-chevron-right', function() {\n move(node, 1);\n });\n },\n\n // init runs again whenever a node is added, without a deinit\n // between, so the listener is replaced rather than stacked\n onInit: function() {\n if (listening) { ge.canvas.removeEventListener('grideditor:after-move', listening); }\n listening = afterMove;\n ge.canvas.addEventListener('grideditor:after-move', listening);\n },\n\n onRefresh: mark,\n\n onDeinit: function() {\n if (listening) { ge.canvas.removeEventListener('grideditor:after-move', listening); }\n listening = null;\n dom.all(ge.canvas, '[data-ge-order]').forEach(function(col) { col.removeAttribute('data-ge-order'); });\n },\n };\n};\n"],
4
+ "sourcesContent": ["/**\n * What a plugin's or a locale's classic script imports in place of the\n * editor: the GridEditor the page already loaded.\n *\n * The build points `import { GridEditor } from '../grideditor.js'` here for\n * the classic scripts, so each registers on the editor the page has rather\n * than bringing its own. Loaded before the editor there is nothing to\n * register on, and saying so is better than a TypeError three calls later.\n */\nvar GridEditor = window.GridEditor;\n\nif (!GridEditor || typeof GridEditor.get !== 'function') {\n throw new Error('grid-editor: load grideditor.js (or grideditor.bundle.min.js) before its plugins, ' +\n 'its locales and grideditor.jquery.js');\n}\n\nexport { GridEditor };\nexport default GridEditor;\n", "/**\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 * Column order for grid-editor.\n *\n * A utility plugin: load this file after the editor and a column's place in\n * its row can differ per breakpoint, with Bootstrap's order-{breakpoint}-*\n * classes. What it can ask the editor for is the handle its factory is called\n * with, described in docs/plugins.md.\n *\n * <script src=\"dist/grideditor.min.js\"></script>\n * <script src=\"dist/plugins/grideditor.order.min.js\"></script>\n *\n * Two arrows in each column's drawer move it one place earlier or later in\n * the view being edited, by numbering the row's columns; the markup does not\n * move. Dragging still moves the markup, as it always has.\n *\n * utilities.order.drawer: false leaves the arrows out, and the panel field is\n * the only control.\n */\nimport { GridEditor } from '../grideditor.js';\nimport * as dom from '../dom.js';\n\nObject.assign(GridEditor.locales.en, {\n 'utility.order': 'Order',\n 'utility.order_first': 'First',\n 'utility.order_last': 'Last',\n 'tool.order_earlier': 'Earlier in this view',\n 'tool.order_later': 'Later in this view',\n 'badge.order': 'Order: {value}',\n});\n\nvar VALUES = ['first', '0', '1', '2', '3', '4', '5', 'last'];\n\n/** Where each value puts a column, as Bootstrap's css has it. */\nvar RANK = { first: -1, last: 6 };\n\n/** A column that carries any class of the family, at any breakpoint. */\nvar CLASS_PATTERN = /(?:^|\\s)order-(?:(?:sm|md|lg|xl|xxl)-)?(?:first|last|[0-5])(?:\\s|$)/;\n\nGridEditor.utilities.order = function(ge) {\n\n var options = Object.assign({ drawer: true }, ge.settings.utilities.order);\n var warnedAboutDrag = false;\n var listening = null; // The after-move listener, while editing\n\n function rank(value) {\n if (value === null) { return 0; }\n\n return RANK[value] !== undefined ? RANK[value] : parseInt(value, 10);\n }\n\n function label(value) {\n if (value === 'first') { return ge.t('utility.order_first'); }\n if (value === 'last') { return ge.t('utility.order_last'); }\n\n return value;\n }\n\n /** The columns of a row in the order a view shows them, given what each one's order is. */\n function visualOrder(columns, read) {\n return columns\n .map(function(element, index) {\n return { element: element, index: index, rank: rank(read(element)) };\n })\n .sort(function(a, b) { return a.rank - b.rank || a.index - b.index; })\n .map(function(entry) { return entry.element; });\n }\n\n function sameOrder(a, b) {\n return a.every(function(element, index) { return element === b[index]; });\n }\n\n /**\n * The values that put n columns in n places, or null past eight: that\n * is how many places Bootstrap's order classes have.\n */\n function slots(count) {\n if (count <= 6) { return VALUES.slice(1, 1 + count); }\n if (count === 7) { return VALUES.slice(1); }\n if (count === 8) { return VALUES.slice(); }\n\n return null;\n }\n\n /**\n * Move a column one place earlier or later in the view being edited.\n *\n * The row's columns are numbered in their new order. When that order is\n * the markup's own, the numbers are taken off instead - unless what is\n * left underneath, the breakpoint below, would then order them some other\n * way, and the numbers are what keep them in the markup's order.\n */\n function move(col, direction) {\n var view = ge.view();\n var columns = dom.children(col.parentElement, '.column');\n var shown = visualOrder(columns, function(column) { return ge.getUtility(column, 'order', view); });\n var from = shown.indexOf(col);\n var to = from + direction;\n\n if (to < 0 || to >= shown.length) { return; }\n\n shown.splice(to, 0, shown.splice(from, 1)[0]);\n\n var values = null;\n if (!sameOrder(shown, columns) || !inheritsMarkupOrder(columns, view)) {\n values = slots(shown.length);\n\n if (!values) {\n ge.warn('a row of ' + shown.length + ' columns cannot be reordered with Bootstrap\\'s ' +\n 'order classes, which have eight places');\n return;\n }\n }\n\n ge.operate(function() {\n shown.forEach(function(element, index) {\n ge.setUtility(element, 'order', values ? values[index] : null, { source: 'tool' });\n });\n });\n }\n\n /** Whether taking this view's classes off leaves the columns in the markup's order. */\n function inheritsMarkupOrder(columns, view) {\n var index = ge.breakpoints.indexOf(view);\n if (index <= 0) { return true; }\n\n var below = ge.breakpoints[index - 1];\n\n return sameOrder(visualOrder(columns, function(column) {\n return ge.getUtility(column, 'order', below);\n }), columns);\n }\n\n /** Whether a row's columns are ordered by class, rather than by the markup, in this view. */\n function ordered(row) {\n return dom.children(row, '.column').some(function(element) {\n return ge.getUtility(element, 'order', ge.view()) !== null;\n });\n }\n\n /** The badge: a column ordered by class in this view says where. */\n function mark(scope) {\n dom.selfAndAll(scope, '.column').forEach(function(col) {\n var value = CLASS_PATTERN.test(col.getAttribute('class') || '')\n ? ge.getUtility(col, 'order', ge.view())\n : null;\n\n if (value === null) {\n col.removeAttribute('data-ge-order');\n } else {\n col.setAttribute('data-ge-order', ge.t('badge.order', { value: label(value) }));\n }\n });\n }\n\n /**\n * A column dropped in a row ordered by class lands where the markup puts\n * it, and shows up where its order does, which is worth saying once.\n */\n function afterMove(e) {\n var payload = e.detail;\n if (warnedAboutDrag || payload.kind !== 'column' || !payload.to) { return; }\n if (!ordered(payload.to.parent)) { return; }\n\n warnedAboutDrag = true;\n ge.warn('a column was dropped in a row whose columns carry order classes in this view: ' +\n 'where it shows is set by those classes, not by where it sits in the markup');\n }\n\n return {\n families: [{\n name: 'order',\n prefix: 'order',\n values: VALUES,\n appliesTo: ['column'],\n labelKey: 'utility.order',\n label: label,\n preview: function(value) {\n return { order: rank(value) };\n },\n }],\n\n drawerTools: function(drawer, node, kind) {\n if (!options.drawer || kind !== 'column') { return; }\n\n ge.createTool(drawer, ge.t('tool.order_earlier'), 'ge-order-earlier', 'bi bi-chevron-left', function() {\n move(node, -1);\n });\n ge.createTool(drawer, ge.t('tool.order_later'), 'ge-order-later', 'bi bi-chevron-right', function() {\n move(node, 1);\n });\n },\n\n // init runs again whenever a node is added, without a deinit\n // between, so the listener is replaced rather than stacked\n onInit: function() {\n if (listening) { ge.canvas.removeEventListener('grideditor:after-move', listening); }\n listening = afterMove;\n ge.canvas.addEventListener('grideditor:after-move', listening);\n },\n\n onRefresh: mark,\n\n onDeinit: function() {\n if (listening) { ge.canvas.removeEventListener('grideditor:after-move', listening); }\n listening = null;\n dom.all(ge.canvas, '[data-ge-order]').forEach(function(col) { col.removeAttribute('data-ge-order'); });\n },\n };\n};\n"],
5
5
  "mappings": "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",
6
6
  "names": ["GridEditor", "all", "root", "selector", "selfAndAll", "root", "selector", "found", "all", "children", "node", "each", "GridEditor", "VALUES", "RANK", "CLASS_PATTERN", "ge", "options", "warnedAboutDrag", "listening", "rank", "value", "label", "visualOrder", "columns", "read", "element", "index", "a", "b", "entry", "sameOrder", "slots", "count", "move", "col", "direction", "view", "children", "shown", "column", "from", "to", "values", "inheritsMarkupOrder", "below", "ordered", "row", "mark", "scope", "selfAndAll", "afterMove", "payload", "drawer", "node", "kind", "all"]
7
7
  }
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "version": 3,
3
3
  "sources": ["../../src/js/register.js", "../../src/js/dom.js", "../../src/js/plugins/grideditor.popup.js"],
4
- "sourcesContent": ["/**\n * What a plugin's or a locale's classic script imports in place of the\n * editor: the GridEditor the page already loaded.\n *\n * The build points `import { GridEditor } from '../grideditor.js'` here for\n * the classic scripts, so each registers on the editor the page has rather\n * than bringing its own. Loaded before the editor there is nothing to\n * register on, and saying so is better than a TypeError three calls later.\n */\nvar GridEditor = window.GridEditor;\n\nif (!GridEditor || typeof GridEditor.get !== 'function') {\n throw new Error('grid-editor: load grideditor.js (or grideditor.bundle.min.js) before its plugins, ' +\n 'its locales and grideditor.jquery.js');\n}\n\nexport { GridEditor };\nexport default GridEditor;\n", "/**\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 the ones 6.x had through jQuery: 400 ms unless the\n * 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 * Popups for grid-editor.\n *\n * A container plugin: load this file after the editor and the toolbar offers\n * a popup: a bootstrap modal and its trigger. What it can ask the editor for is the handle its factory is\n * called with, described in docs/plugins.md.\n *\n * <script src=\"dist/grideditor.min.js\"></script>\n * <script src=\"dist/plugins/grideditor.popup.min.js\"></script>\n */\nimport { GridEditor } from '../grideditor.js';\nimport * as dom from '../dom.js';\n\nObject.assign(GridEditor.locales.en, {\n 'container.add_popup': 'Popup',\n 'container.popup_title': 'Title',\n 'container.popup_trigger': 'Open',\n 'tool.toggle_popup': 'Fold this popup away while editing',\n});\n\nGridEditor.containers.popup = function(ge) {\n\n function popupIdOf(container) {\n return container.getAttribute('data-ge-popup-id');\n }\n\n /** Whether a popup with this id is on the canvas. */\n function popupExists(id) {\n return dom.all(ge.canvas, '[data-ge-popup-id]').some(function(popup) {\n return popupIdOf(popup) === id;\n });\n }\n\n function wirePopupTriggers() {\n dom.all(ge.canvas, '[data-ge-popup-target]').forEach(function(trigger) {\n dom.addClass(trigger, 'ge-popup-trigger');\n var wanted = trigger.getAttribute('data-ge-popup-target');\n\n // Bootstrap's own attributes are written at getHtml time, not\n // while editing, so a click here cannot open a real modal\n trigger.removeAttribute('data-bs-toggle');\n trigger.removeAttribute('data-bs-target');\n\n if (popupExists(wanted)) {\n dom.removeClass(trigger, 'ge-popup-orphan');\n return;\n }\n\n var column = trigger.closest('.column');\n var nearby = column ? dom.all(column, '[data-ge-popup-id]') : [];\n\n if (nearby.length === 1) {\n trigger.setAttribute('data-ge-popup-target', popupIdOf(nearby[0]));\n dom.removeClass(trigger, 'ge-popup-orphan');\n return;\n }\n\n dom.addClass(trigger, 'ge-popup-orphan');\n\n ge.operate(function() {\n ge.emit('popup-orphan', ge.payloadFor('popup', trigger, {\n parent: trigger.parentElement,\n source: 'api',\n missing: wanted,\n }));\n });\n });\n }\n\n function writePopupTriggerAttributes() {\n dom.all(ge.canvas, '[data-ge-popup-target]').forEach(function(trigger) {\n var wanted = trigger.getAttribute('data-ge-popup-target');\n\n // The warning marking is editing furniture, whether or not\n // the trigger can be wired up\n dom.removeClass(trigger, 'ge-popup-orphan');\n dom.dropEmptyClass(trigger);\n\n if (!popupExists(wanted)) { return; }\n\n trigger.setAttribute('data-bs-toggle', 'modal');\n trigger.setAttribute('data-bs-target', '#' + wanted);\n });\n }\n\n return {\n labelKey: 'container.add_popup',\n paneKind: 'popup',\n\n // Triggers are markup the host owns, anywhere in the canvas, so they\n // are looked at whenever the canvas is initialized rather than only\n // when a popup is touched\n onInit: wirePopupTriggers,\n onDeinit: writePopupTriggerAttributes,\n\n create: function(options) {\n var id = ge.containerId('popup');\n var container = dom.element('div', { 'data-ge-container': 'popup', 'data-ge-popup-id': id });\n\n if (options.trigger !== false) {\n container.appendChild(dom.element('button', {\n type: 'button',\n 'class': 'btn btn-primary ge-popup-trigger',\n 'data-ge-popup-target': id,\n }, options.trigger_label || ge.t('container.popup_trigger')));\n }\n\n var modal = container.appendChild(dom.element('div', {\n 'class': 'modal fade',\n tabindex: '-1',\n 'aria-hidden': 'true',\n id: id,\n }));\n var dialog = modal.appendChild(dom.element('div', { 'class': 'modal-dialog' }));\n if (options.size) { dom.addClass(dialog, 'modal-' + options.size); }\n\n var content = dialog.appendChild(dom.element('div', { 'class': 'modal-content' }));\n var header = content.appendChild(dom.element('div', { 'class': 'modal-header' }));\n header.appendChild(dom.element('h5', { 'class': 'modal-title' }))\n .appendChild(dom.element('span', { 'class': 'ge-pane-label' },\n options.title || ge.t('container.popup_title')));\n header.appendChild(dom.create('<button type=\"button\" class=\"btn-close\" data-bs-dismiss=\"modal\" aria-label=\"Close\"></button>'));\n content.appendChild(dom.element('div', { 'class': 'modal-body' })).appendChild(ge.defaultRegion());\n\n return container;\n },\n\n mark: function(container) {\n // Nothing in a popup may reach Bootstrap while editing:\n // the modal is rendered unfolded and static, and a real\n // modal opening over it would be the editor fighting\n // itself\n dom.all(container, '[data-bs-dismiss]').forEach(function(dismiss) {\n ge.suspendToggles(dismiss);\n });\n dom.all(container, '.modal-title').forEach(function(title) {\n ge.makeLabelEditable(ge.labelIn(title));\n });\n },\n\n unmark: function(container) {\n ge.resumeToggles(container);\n dom.removeClass(container, 'ge-popup-collapsed');\n ge.unwrapLabels(container);\n },\n\n /** A page of unfolded modals stays workable if they can be folded away. */\n tools: function(drawer, container) {\n ge.createTool(drawer, ge.t('tool.toggle_popup'), 'ge-toggle-popup', 'bi bi-chevron-bar-contract',\n function() {\n dom.toggleClass(container, 'ge-popup-collapsed');\n });\n },\n };\n};\n"],
4
+ "sourcesContent": ["/**\n * What a plugin's or a locale's classic script imports in place of the\n * editor: the GridEditor the page already loaded.\n *\n * The build points `import { GridEditor } from '../grideditor.js'` here for\n * the classic scripts, so each registers on the editor the page has rather\n * than bringing its own. Loaded before the editor there is nothing to\n * register on, and saying so is better than a TypeError three calls later.\n */\nvar GridEditor = window.GridEditor;\n\nif (!GridEditor || typeof GridEditor.get !== 'function') {\n throw new Error('grid-editor: load grideditor.js (or grideditor.bundle.min.js) before its plugins, ' +\n 'its locales and grideditor.jquery.js');\n}\n\nexport { GridEditor };\nexport default GridEditor;\n", "/**\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 * Popups for grid-editor.\n *\n * A container plugin: load this file after the editor and the toolbar offers\n * a popup: a bootstrap modal and its trigger. What it can ask the editor for is the handle its factory is\n * called with, described in docs/plugins.md.\n *\n * <script src=\"dist/grideditor.min.js\"></script>\n * <script src=\"dist/plugins/grideditor.popup.min.js\"></script>\n */\nimport { GridEditor } from '../grideditor.js';\nimport * as dom from '../dom.js';\n\nObject.assign(GridEditor.locales.en, {\n 'container.add_popup': 'Popup',\n 'container.popup_title': 'Title',\n 'container.popup_trigger': 'Open',\n 'tool.toggle_popup': 'Fold this popup away while editing',\n});\n\nGridEditor.containers.popup = function(ge) {\n\n function popupIdOf(container) {\n return container.getAttribute('data-ge-popup-id');\n }\n\n /** Whether a popup with this id is on the canvas. */\n function popupExists(id) {\n return dom.all(ge.canvas, '[data-ge-popup-id]').some(function(popup) {\n return popupIdOf(popup) === id;\n });\n }\n\n function wirePopupTriggers() {\n dom.all(ge.canvas, '[data-ge-popup-target]').forEach(function(trigger) {\n dom.addClass(trigger, 'ge-popup-trigger');\n var wanted = trigger.getAttribute('data-ge-popup-target');\n\n // Bootstrap's own attributes are written at getHtml time, not\n // while editing, so a click here cannot open a real modal\n trigger.removeAttribute('data-bs-toggle');\n trigger.removeAttribute('data-bs-target');\n\n if (popupExists(wanted)) {\n dom.removeClass(trigger, 'ge-popup-orphan');\n return;\n }\n\n var column = trigger.closest('.column');\n var nearby = column ? dom.all(column, '[data-ge-popup-id]') : [];\n\n if (nearby.length === 1) {\n trigger.setAttribute('data-ge-popup-target', popupIdOf(nearby[0]));\n dom.removeClass(trigger, 'ge-popup-orphan');\n return;\n }\n\n dom.addClass(trigger, 'ge-popup-orphan');\n\n ge.operate(function() {\n ge.emit('popup-orphan', ge.payloadFor('popup', trigger, {\n parent: trigger.parentElement,\n source: 'api',\n missing: wanted,\n }));\n });\n });\n }\n\n function writePopupTriggerAttributes() {\n dom.all(ge.canvas, '[data-ge-popup-target]').forEach(function(trigger) {\n var wanted = trigger.getAttribute('data-ge-popup-target');\n\n // The warning marking is editing furniture, whether or not\n // the trigger can be wired up\n dom.removeClass(trigger, 'ge-popup-orphan');\n dom.dropEmptyClass(trigger);\n\n if (!popupExists(wanted)) { return; }\n\n trigger.setAttribute('data-bs-toggle', 'modal');\n trigger.setAttribute('data-bs-target', '#' + wanted);\n });\n }\n\n return {\n labelKey: 'container.add_popup',\n paneKind: 'popup',\n\n // Triggers are markup the host owns, anywhere in the canvas, so they\n // are looked at whenever the canvas is initialized rather than only\n // when a popup is touched\n onInit: wirePopupTriggers,\n onDeinit: writePopupTriggerAttributes,\n\n create: function(options) {\n var id = ge.containerId('popup');\n var container = dom.element('div', { 'data-ge-container': 'popup', 'data-ge-popup-id': id });\n\n if (options.trigger !== false) {\n container.appendChild(dom.element('button', {\n type: 'button',\n 'class': 'btn btn-primary ge-popup-trigger',\n 'data-ge-popup-target': id,\n }, options.trigger_label || ge.t('container.popup_trigger')));\n }\n\n var modal = container.appendChild(dom.element('div', {\n 'class': 'modal fade',\n tabindex: '-1',\n 'aria-hidden': 'true',\n id: id,\n }));\n var dialog = modal.appendChild(dom.element('div', { 'class': 'modal-dialog' }));\n if (options.size) { dom.addClass(dialog, 'modal-' + options.size); }\n\n var content = dialog.appendChild(dom.element('div', { 'class': 'modal-content' }));\n var header = content.appendChild(dom.element('div', { 'class': 'modal-header' }));\n header.appendChild(dom.element('h5', { 'class': 'modal-title' }))\n .appendChild(dom.element('span', { 'class': 'ge-pane-label' },\n options.title || ge.t('container.popup_title')));\n header.appendChild(dom.create('<button type=\"button\" class=\"btn-close\" data-bs-dismiss=\"modal\" aria-label=\"Close\"></button>'));\n content.appendChild(dom.element('div', { 'class': 'modal-body' })).appendChild(ge.defaultRegion());\n\n return container;\n },\n\n mark: function(container) {\n // Nothing in a popup may reach Bootstrap while editing:\n // the modal is rendered unfolded and static, and a real\n // modal opening over it would be the editor fighting\n // itself\n dom.all(container, '[data-bs-dismiss]').forEach(function(dismiss) {\n ge.suspendToggles(dismiss);\n });\n dom.all(container, '.modal-title').forEach(function(title) {\n ge.makeLabelEditable(ge.labelIn(title));\n });\n },\n\n unmark: function(container) {\n ge.resumeToggles(container);\n dom.removeClass(container, 'ge-popup-collapsed');\n ge.unwrapLabels(container);\n },\n\n /** A page of unfolded modals stays workable if they can be folded away. */\n tools: function(drawer, container) {\n ge.createTool(drawer, ge.t('tool.toggle_popup'), 'ge-toggle-popup', 'bi bi-chevron-bar-contract',\n function() {\n dom.toggleClass(container, 'ge-popup-collapsed');\n });\n },\n };\n};\n"],
5
5
  "mappings": "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",
6
6
  "names": ["GridEditor", "all", "root", "selector", "parse", "html", "template", "create", "nodes", "i", "element", "tag", "attributes", "text", "node", "name", "value", "addClass", "node", "names", "split", "name", "removeClass", "toggleClass", "state", "split", "names", "dropEmptyClass", "node", "GridEditor", "ge", "popupIdOf", "container", "popupExists", "id", "all", "popup", "wirePopupTriggers", "trigger", "addClass", "wanted", "removeClass", "column", "nearby", "writePopupTriggerAttributes", "dropEmptyClass", "options", "element", "modal", "dialog", "content", "header", "create", "dismiss", "title", "drawer", "toggleClass"]
7
7
  }
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "version": 3,
3
3
  "sources": ["../../src/js/register.js", "../../src/js/dom.js", "../../src/js/plugins/grideditor.sections.js"],
4
- "sourcesContent": ["/**\n * What a plugin's or a locale's classic script imports in place of the\n * editor: the GridEditor the page already loaded.\n *\n * The build points `import { GridEditor } from '../grideditor.js'` here for\n * the classic scripts, so each registers on the editor the page has rather\n * than bringing its own. Loaded before the editor there is nothing to\n * register on, and saying so is better than a TypeError three calls later.\n */\nvar GridEditor = window.GridEditor;\n\nif (!GridEditor || typeof GridEditor.get !== 'function') {\n throw new Error('grid-editor: load grideditor.js (or grideditor.bundle.min.js) before its plugins, ' +\n 'its locales and grideditor.jquery.js');\n}\n\nexport { GridEditor };\nexport default GridEditor;\n", "/**\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 the ones 6.x had through jQuery: 400 ms unless the\n * 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 * Sections for grid-editor.\n *\n * A feature plugin: load this file after the editor and the canvas can hold\n * sections - Bootstrap's .container, .container-fluid and .container-{bp} -\n * each grouping rows at a width of its own. What it can ask the editor for is\n * the handle its factory is called with, described in docs/plugins.md.\n *\n * <script src=\"dist/grideditor.min.js\"></script>\n * <script src=\"dist/plugins/grideditor.sections.min.js\"></script>\n *\n * Called sections, not containers, because a container is what the tabs,\n * accordion, popup and card plugins make. A section is recognised by its\n * Bootstrap class alone, and only as a child of the canvas: a .container\n * somewhere inside an element's markup is that element's business.\n *\n * sections.widths narrows the widths the field offers.\n */\nimport { GridEditor } from '../grideditor.js';\nimport * as dom from '../dom.js';\n\nObject.assign(GridEditor.locales.en, {\n 'section.add': 'Section',\n 'section.width': 'Width',\n 'section.fixed': 'Fixed',\n 'section.fluid': 'Full width',\n 'section.from': 'Fixed from {breakpoint}',\n 'tool.add_row_to_section': 'Add row',\n 'tool.delete_section': 'Remove section',\n 'confirm.delete_section': 'Delete this section and everything in it?',\n});\n\n/** Each width, and the class that gives it. */\nvar WIDTHS = {\n fixed: 'container',\n fluid: 'container-fluid',\n sm: 'container-sm',\n md: 'container-md',\n lg: 'container-lg',\n xl: 'container-xl',\n xxl: 'container-xxl',\n};\n\nvar ORDER = ['fixed', 'sm', 'md', 'lg', 'xl', 'xxl', 'fluid'];\n\nGridEditor.features.sections = function(ge) {\n\n var options = Object.assign({ widths: ORDER }, ge.settings.sections);\n\n function widthOf(section) {\n var found = null;\n\n Object.keys(WIDTHS).forEach(function(width) {\n if (!found && dom.hasClass(section, WIDTHS[width])) { found = width; }\n });\n\n return found;\n }\n\n function isSection(node) {\n return node.parentElement === ge.canvas && widthOf(node) !== null;\n }\n\n function sections() {\n return dom.children(ge.canvas).filter(isSection);\n }\n\n function label(width) {\n if (width === 'fixed') { return ge.t('section.fixed'); }\n if (width === 'fluid') { return ge.t('section.fluid'); }\n\n return ge.t('section.from', { breakpoint: width });\n }\n\n /**\n * Change a section's width, announced like a utility: the width is its\n * one container class, the same at every breakpoint.\n */\n function setWidth(section, width, source) {\n var from = widthOf(section);\n if (from === width || !WIDTHS[width]) { return false; }\n\n return ge.operate(function() {\n var payload = ge.payloadFor('section', section, {\n family: 'section',\n breakpoint: 'all',\n tiers: [],\n from: from,\n to: width,\n source: source || 'api',\n });\n\n if (!ge.emit('before-utility', payload)) {\n var select = dom.one(ge.detailsOf(section), '.ge-section-width select');\n if (select) { select.value = from; }\n return false;\n }\n\n dom.removeClass(section, WIDTHS[from]);\n dom.addClass(section, WIDTHS[width]);\n ge.emit('after-utility', payload);\n\n return true;\n });\n }\n\n function widthField(section) {\n var select = dom.element('select', { 'class': 'form-select form-select-sm' });\n var current = widthOf(section);\n var offered = options.widths.indexOf(current) === -1 ? options.widths.concat([current]) : options.widths;\n\n ORDER.forEach(function(width) {\n if (offered.indexOf(width) === -1) { return; }\n select.appendChild(dom.element('option', { value: width }, label(width)));\n });\n\n select.value = current;\n select.addEventListener('change', function() { setWidth(section, this.value, 'panel'); });\n\n var field = dom.element('label', { 'class': 'ge-utility ge-section-width' });\n field.appendChild(dom.element('span', { 'class': 'ge-utility-label' }, ge.t('section.width')));\n field.appendChild(select);\n\n return field;\n }\n\n function createControls(section) {\n var drawer = dom.element('div', { 'class': 'ge-tools-drawer ge-section-drawer' });\n section.insertBefore(drawer, section.firstChild);\n\n ge.createMoveTool(drawer);\n ge.addSettingsTool(drawer, section, ge.settings.section_classes || []).appendChild(widthField(section));\n\n ge.createTool(drawer, ge.t('tool.delete_section'), 'ge-delete-section', 'bi bi-trash', function() {\n ge.deleteNode('section', section, ge.t('confirm.delete_section'), function(removed) {\n dom.slideUp(section, removed);\n });\n });\n\n ge.createTool(drawer, ge.t('tool.add_row_to_section'), 'ge-add-row', 'bi bi-plus-circle', function() {\n ge.place(ge.rowFromLayout([12]), 'row', { appendTo: section });\n });\n }\n\n function mark() {\n sections().forEach(function(section) {\n dom.addClass(section, 'ge-section');\n if (!dom.child(section, '.ge-tools-drawer')) { createControls(section); }\n });\n }\n\n function unmark() {\n dom.children(ge.canvas, '.ge-section').forEach(function(section) {\n dom.removeClass(section, 'ge-section');\n });\n }\n\n /** createSection(options): a section, detached unless a placement is given. */\n function createSection(settings) {\n settings = settings || {};\n\n var section = dom.element('div', { 'class': WIDTHS[settings.width] || WIDTHS.fixed });\n\n (settings.rows || [[12]]).forEach(function(layout) {\n section.appendChild(ge.rowFromLayout(layout));\n });\n\n return ge.place(section, 'section', settings);\n }\n\n return {\n methods: {\n createSection: createSection,\n },\n\n kindOf: function(node) {\n return dom.hasClass(node, 'ge-section') ? 'section' : null;\n },\n\n // A section is a block the canvas moves, and a region rows move in\n blocks: '.ge-section',\n regions: '.ge-section',\n\n /** A section goes on the canvas and nowhere else, and holds rows and nothing else. */\n accepts: function(region, node) {\n if (dom.hasClass(node, 'ge-section') || isSectionMade(node)) { return region === ge.canvas; }\n if (dom.hasClass(region, 'ge-section')) { return dom.hasClass(node, 'row'); }\n\n return true;\n },\n\n toolbar: [{\n labelKey: 'section.add',\n kind: 'section',\n create: function() { return createSection(); },\n }],\n\n onInit: mark,\n onDeinit: unmark,\n };\n\n /** A section the toolbar just made, before init has marked it. */\n function isSectionMade(node) {\n return !node.parentElement && widthOf(node) !== null;\n }\n};\n"],
5
- "mappings": "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",
4
+ "sourcesContent": ["/**\n * What a plugin's or a locale's classic script imports in place of the\n * editor: the GridEditor the page already loaded.\n *\n * The build points `import { GridEditor } from '../grideditor.js'` here for\n * the classic scripts, so each registers on the editor the page has rather\n * than bringing its own. Loaded before the editor there is nothing to\n * register on, and saying so is better than a TypeError three calls later.\n */\nvar GridEditor = window.GridEditor;\n\nif (!GridEditor || typeof GridEditor.get !== 'function') {\n throw new Error('grid-editor: load grideditor.js (or grideditor.bundle.min.js) before its plugins, ' +\n 'its locales and grideditor.jquery.js');\n}\n\nexport { GridEditor };\nexport default GridEditor;\n", "/**\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 * Sections for grid-editor.\n *\n * A feature plugin: load this file after the editor and the canvas can hold\n * sections - Bootstrap's .container, .container-fluid and .container-{bp} -\n * each grouping rows at a width of its own. What it can ask the editor for is\n * the handle its factory is called with, described in docs/plugins.md.\n *\n * <script src=\"dist/grideditor.min.js\"></script>\n * <script src=\"dist/plugins/grideditor.sections.min.js\"></script>\n *\n * Called sections, not containers, because a container is what the tabs,\n * accordion, popup and card plugins make. A section is recognised by its\n * Bootstrap class alone, and only as a child of the canvas: a .container\n * somewhere inside an element's markup is that element's business.\n *\n * sections.widths narrows the widths the field offers.\n */\nimport { GridEditor } from '../grideditor.js';\nimport * as dom from '../dom.js';\n\nObject.assign(GridEditor.locales.en, {\n 'section.add': 'Section',\n 'section.width': 'Width',\n 'section.fixed': 'Fixed',\n 'section.fluid': 'Full width',\n 'section.from': 'Fixed from {breakpoint}',\n 'tool.add_row_to_section': 'Add row',\n 'tool.delete_section': 'Remove section',\n 'confirm.delete_section': 'Delete this section and everything in it?',\n});\n\n/** Each width, and the class that gives it. */\nvar WIDTHS = {\n fixed: 'container',\n fluid: 'container-fluid',\n sm: 'container-sm',\n md: 'container-md',\n lg: 'container-lg',\n xl: 'container-xl',\n xxl: 'container-xxl',\n};\n\nvar ORDER = ['fixed', 'sm', 'md', 'lg', 'xl', 'xxl', 'fluid'];\n\nGridEditor.features.sections = function(ge) {\n\n var options = Object.assign({ widths: ORDER }, ge.settings.sections);\n\n function widthOf(section) {\n var found = null;\n\n Object.keys(WIDTHS).forEach(function(width) {\n if (!found && dom.hasClass(section, WIDTHS[width])) { found = width; }\n });\n\n return found;\n }\n\n function isSection(node) {\n return node.parentElement === ge.canvas && widthOf(node) !== null;\n }\n\n function sections() {\n return dom.children(ge.canvas).filter(isSection);\n }\n\n function label(width) {\n if (width === 'fixed') { return ge.t('section.fixed'); }\n if (width === 'fluid') { return ge.t('section.fluid'); }\n\n return ge.t('section.from', { breakpoint: width });\n }\n\n /**\n * Change a section's width, announced like a utility: the width is its\n * one container class, the same at every breakpoint.\n */\n function setWidth(section, width, source) {\n var from = widthOf(section);\n if (from === width || !WIDTHS[width]) { return false; }\n\n return ge.operate(function() {\n var payload = ge.payloadFor('section', section, {\n family: 'section',\n breakpoint: 'all',\n tiers: [],\n from: from,\n to: width,\n source: source || 'api',\n });\n\n if (!ge.emit('before-utility', payload)) {\n var select = dom.one(ge.detailsOf(section), '.ge-section-width select');\n if (select) { select.value = from; }\n return false;\n }\n\n dom.removeClass(section, WIDTHS[from]);\n dom.addClass(section, WIDTHS[width]);\n ge.emit('after-utility', payload);\n\n return true;\n });\n }\n\n function widthField(section) {\n var select = dom.element('select', { 'class': 'form-select form-select-sm' });\n var current = widthOf(section);\n var offered = options.widths.indexOf(current) === -1 ? options.widths.concat([current]) : options.widths;\n\n ORDER.forEach(function(width) {\n if (offered.indexOf(width) === -1) { return; }\n select.appendChild(dom.element('option', { value: width }, label(width)));\n });\n\n select.value = current;\n select.addEventListener('change', function() { setWidth(section, this.value, 'panel'); });\n\n var field = dom.element('label', { 'class': 'ge-utility ge-section-width' });\n field.appendChild(dom.element('span', { 'class': 'ge-utility-label' }, ge.t('section.width')));\n field.appendChild(select);\n\n return field;\n }\n\n function createControls(section) {\n var drawer = dom.element('div', { 'class': 'ge-tools-drawer ge-section-drawer' });\n section.insertBefore(drawer, section.firstChild);\n\n ge.createMoveTool(drawer);\n ge.addSettingsTool(drawer, section, ge.settings.section_classes || []).appendChild(widthField(section));\n\n ge.createTool(drawer, ge.t('tool.delete_section'), 'ge-delete-section', 'bi bi-trash', function() {\n ge.deleteNode('section', section, ge.t('confirm.delete_section'), function(removed) {\n dom.slideUp(section, removed);\n });\n });\n\n ge.createTool(drawer, ge.t('tool.add_row_to_section'), 'ge-add-row', 'bi bi-plus-circle', function() {\n ge.place(ge.rowFromLayout([12]), 'row', { appendTo: section });\n });\n }\n\n function mark() {\n sections().forEach(function(section) {\n dom.addClass(section, 'ge-section');\n if (!dom.child(section, '.ge-tools-drawer')) { createControls(section); }\n });\n }\n\n function unmark() {\n dom.children(ge.canvas, '.ge-section').forEach(function(section) {\n dom.removeClass(section, 'ge-section');\n });\n }\n\n /** createSection(options): a section, detached unless a placement is given. */\n function createSection(settings) {\n settings = settings || {};\n\n var section = dom.element('div', { 'class': WIDTHS[settings.width] || WIDTHS.fixed });\n\n (settings.rows || [[12]]).forEach(function(layout) {\n section.appendChild(ge.rowFromLayout(layout));\n });\n\n return ge.place(section, 'section', settings);\n }\n\n return {\n methods: {\n createSection: createSection,\n },\n\n kindOf: function(node) {\n return dom.hasClass(node, 'ge-section') ? 'section' : null;\n },\n\n // A section is a block the canvas moves, and a region rows move in\n blocks: '.ge-section',\n regions: '.ge-section',\n\n /** A section goes on the canvas and nowhere else, and holds rows and nothing else. */\n accepts: function(region, node) {\n if (dom.hasClass(node, 'ge-section') || isSectionMade(node)) { return region === ge.canvas; }\n if (dom.hasClass(region, 'ge-section')) { return dom.hasClass(node, 'row'); }\n\n return true;\n },\n\n toolbar: [{\n labelKey: 'section.add',\n kind: 'section',\n create: function() { return createSection(); },\n }],\n\n onInit: mark,\n onDeinit: unmark,\n };\n\n /** A section the toolbar just made, before init has marked it. */\n function isSectionMade(node) {\n return !node.parentElement && widthOf(node) !== null;\n }\n};\n"],
5
+ "mappings": "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",
6
6
  "names": ["GridEditor", "one", "root", "selector", "children", "node", "selector", "each", "child", "element", "tag", "attributes", "text", "node", "name", "value", "addClass", "node", "names", "split", "name", "removeClass", "hasClass", "node", "name", "split", "names", "hide", "node", "visible", "node", "DEFAULT_DURATION", "animateAway", "node", "frames", "duration", "done", "finish", "hide", "visible", "animation", "called", "once", "slideUp", "style", "GridEditor", "WIDTHS", "ORDER", "ge", "options", "widthOf", "section", "found", "width", "hasClass", "isSection", "node", "sections", "children", "label", "setWidth", "source", "from", "payload", "select", "one", "removeClass", "addClass", "widthField", "element", "current", "offered", "field", "createControls", "drawer", "removed", "slideUp", "mark", "child", "unmark", "createSection", "settings", "layout", "region", "isSectionMade"]
7
7
  }