feat(demo): add story 1 — Sorano: Rock and Time

This commit is contained in:
2026-06-20 21:19:57 +02:00
parent 42ed59a6b3
commit 8f87155c1d
5508 changed files with 1595740 additions and 124 deletions
@@ -0,0 +1,24 @@
# app
## Project setup
```
yarn install
```
### Compiles and hot-reloads for development
```
yarn serve
```
### Compiles and minifies for production
```
yarn build
```
### Lints and fixes files
```
yarn lint
```
### Customize configuration
See [Configuration Reference](https://cli.vuejs.org/config/).
@@ -0,0 +1,5 @@
module.exports = {
presets: [
'@vue/cli-plugin-babel/preset',
],
};
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
@@ -0,0 +1,24 @@
{
"name": "nextgen-editor",
"version": "0.1.0",
"private": true,
"scripts": {
"dev": "vue-cli-service serve",
"serve": "vue-cli-service serve",
"build": "vue-cli-service build",
"lint": "vue-cli-service lint"
},
"devDependencies": {
"@vue/cli-plugin-babel": "~4.5.13",
"@vue/cli-plugin-eslint": "~4.5.13",
"@vue/cli-service": "~4.5.13",
"@vue/eslint-config-airbnb": "^5.3.0",
"babel-eslint": "^10.1.0",
"directory-named-webpack-plugin": "^4.0.1",
"eslint": "^7.32.0",
"eslint-plugin-import": "^2.24.2",
"eslint-plugin-vue": "^7.18.0",
"node-sass": "^6.0.1",
"sass-loader": "^12.1.0"
}
}
@@ -0,0 +1,55 @@
window.nextgenEditor.addHook('hookInit', () => {
window.nextgenEditor.addButtonGroup('shortcode-core-align', {
icon: '<svg viewBox="0 0 24 24" xmlns="http://www.w3.org/2000/svg"><path d="M2.75 1h-.01c-.56 0-1 .44-1 1v20c0 .55.44.99 1 .99.55-.01.99-.45.99-1.01v-20c0-.56-.45-1-1-1z"/><rect style="width:11px;height:6px;" x="5.25" rx="1.5" y="5"/><rect style="width:17px;height:6px;" x="5.25" rx="1.5" y="13"/></svg>',
label: 'SC Align',
});
});
window.nextgenEditor.addShortcode('left', {
type: 'block',
plugin: 'shortcode-core',
title: 'Align Left',
button: {
group: 'shortcode-core-align',
label: 'Align Left',
},
content() {
return '<div style="text-align:left">{{content_editable}}</div>';
},
});
window.nextgenEditor.addShortcode('center', {
type: 'block',
title: 'Align Center',
button: {
group: 'shortcode-core-align',
label: 'Align Center',
},
content() {
return '<div style="text-align:center">{{content_editable}}</div>';
},
});
window.nextgenEditor.addShortcode('right', {
type: 'block',
title: 'Align Right',
button: {
group: 'shortcode-core-align',
label: 'Align Right',
},
content() {
return '<div style="text-align:right">{{content_editable}}</div>';
},
});
window.nextgenEditor.addShortcode('justify', {
type: 'block',
title: 'Justify',
button: {
group: 'shortcode-core-align',
label: 'Justify',
},
content() {
return '<div style="text-align:justify">{{content_editable}}</div>';
},
});
@@ -0,0 +1,22 @@
window.nextgenEditor.addShortcode('color', {
type: 'inline',
plugin: 'shortcode-core',
title: 'Color',
button: {
group: 'shortcode-core',
label: 'Color',
icon: '<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24"><path d="M9.3 24a1 1 0 00.756-.345L22.523 9.277a2 2 0 00-.212-2.822l-2.45-2.105a1 1 0 00-1.3 1.517l2.072 1.775a.5.5 0 01.052.707l-7.8 9a.25.25 0 01-.423-.251l4.671-12.614a2 2 0 00-1.181-2.57L12.609.675a1 1 0 10-.7 1.875l2.876 1.065a.5.5 0 01.295.643l-4.602 12.419a.25.25 0 01-.485-.087V1.5a1.5 1.5 0 00-1.5-1.5h-6a1.5 1.5 0 00-1.5 1.5v21a1.5 1.5 0 001.5 1.5zM3.493 9.75a.5.5 0 01.5-.5h3a.5.5 0 01.5.5v3a.5.5 0 01-.5.5h-3a.5.5 0 01-.5-.5zm0-3.75V3a.5.5 0 01.5-.5h3a.5.5 0 01.5.5v3a.5.5 0 01-.5.5h-3a.5.5 0 01-.5-.5zm0 10.5a.5.5 0 01.5-.5h3a.5.5 0 01.5.5v3a.5.5 0 01-.5.5h-3a.5.5 0 01-.5-.5z"/></svg>',
},
attributes: {
color: {
type: String,
title: 'Color',
bbcode: true,
widget: 'input-text',
default: '',
},
},
content({ attributes }) {
return `<span style="color:${attributes.color}">{{content_editable}}</span>`;
},
});
@@ -0,0 +1,58 @@
window.nextgenEditor.addShortcode('columns', {
type: 'block',
plugin: 'shortcode-core',
title: 'Columns',
button: {
group: 'shortcode-core',
label: 'Columns',
icon: '<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24"><path d="M22 0H2a2 2 0 00-2 2v20a2 2 0 002 2h20a2 2 0 002-2V2a2 2 0 00-2-2zm-7 2.5v19a.5.5 0 01-.5.5h-5a.5.5 0 01-.5-.5v-19a.5.5 0 01.5-.5h5a.5.5 0 01.5.5zM2.5 2h4a.5.5 0 01.5.5v19a.5.5 0 01-.5.5h-4a.5.5 0 01-.5-.5v-19a.5.5 0 01.5-.5zm19 20h-4a.5.5 0 01-.5-.5v-19a.5.5 0 01.5-.5h4a.5.5 0 01.5.5v19a.5.5 0 01-.5.5z"/></svg>',
},
attributes: {
count: {
type: Number,
title: 'Count',
widget: {
type: 'input-number',
min: 1,
max: 12,
},
default: 2,
},
width: {
type: String,
title: 'Width',
widget: 'input-text',
default: 'auto',
},
gap: {
type: String,
title: 'Gap',
widget: 'input-text',
default: 'normal',
},
rule: {
type: String,
title: 'Rule',
widget: 'input-text',
default: '',
},
},
titlebar({ attributes }) {
return `columns: <strong>${attributes.count}</strong>`;
},
content({ attributes }) {
const styles = []
.concat([
`columns:${attributes.count} ${attributes.width}`,
`-moz-columns:${attributes.count} ${attributes.width}`,
`column-gap:${attributes.gap}`,
`-moz-column-gap:${attributes.gap}`,
attributes.rule ? `column-rule:${attributes.rule}` : null,
attributes.rule ? `-moz-column-rule:${attributes.rule}` : null,
])
.filter((item) => !!item)
.join(';');
return `<div style="${styles}">{{content_editable}}</div>`;
},
});
@@ -0,0 +1,8 @@
shortcode-block[name="details"] summary {
margin: 8px 8px;
}
shortcode-block[name="details"] summary > p {
display: inline;
margin: 0;
}
@@ -0,0 +1,50 @@
window.nextgenEditor.addShortcode('details', {
type: 'block',
plugin: 'shortcode-core',
title: 'Details',
button: {
group: 'shortcode-core',
label: 'Details',
icon: '<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24"><path d="M2.2 8.348a1 1 0 001.4.2l3.465-2.6a1.5 1.5 0 000-2.4L3.6.948a1 1 0 00-1.2 1.6l2.666 2a.25.25 0 010 .4l-2.666 2a1 1 0 00-.2 1.4zM23 21.248H1a1 1 0 000 2h22a1 1 0 000-2zM23 16.248H1a1 1 0 000 2h22a1 1 0 000-2zM23 11.248H1a1 1 0 000 2h22a1 1 0 000-2zM24 7.248a1 1 0 00-1-1H12a1 1 0 000 2h11a1 1 0 001-1zM12 3.248h11a1 1 0 000-2H12a1 1 0 000 2z"/></svg>',
},
attributes: {
summary: {
type: String,
title: 'Summary',
bbcode: true,
widget: 'input-text',
default: '',
},
class: {
type: String,
title: 'Class',
widget: 'input-text',
default: '',
},
},
titlebar({ attributes }) {
return attributes.class
? `class: <strong>${attributes.class}</strong>`
: '';
},
content({ attributes }) {
let output = '';
output += `<details class="${attributes.class || ''}" open>`;
if (attributes.summary) {
output += `<summary>${attributes.summary}</summary>`;
}
output += '{{content_editable}}';
output += '</details>';
return output;
},
preserve: {
block: [
'details',
'summary',
],
},
});
@@ -0,0 +1,47 @@
window.nextgenEditor.addShortcode('div', {
type: 'block',
plugin: 'shortcode-core',
title: 'Div',
button: {
group: 'shortcode-core',
label: 'Div',
icon: '<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24"><path d="M24 4.5a3 3 0 00-3-3H3a3 3 0 00-3 3v15a3 3 0 003 3h18a3 3 0 003-3zM3 5a1 1 0 111 1 1 1 0 01-1-1zm3 0a1 1 0 111 1 1 1 0 01-1-1zm3 0a1 1 0 111 1 1 1 0 01-1-1zm13 14.5a1 1 0 01-1 1H3a1 1 0 01-1-1V9a.5.5 0 01.5-.5h19a.5.5 0 01.5.5z"/><path d="M7.75 12a.75.75 0 00.75.75.25.25 0 01.25.25v4a.75.75 0 001.5 0v-4a.25.25 0 01.25-.25.75.75 0 000-1.5h-2a.75.75 0 00-.75.75zM4 17.75a.75.75 0 00.75-.75v-1a.25.25 0 01.5 0v1a.75.75 0 001.5 0v-5a.75.75 0 00-1.5 0v2a.25.25 0 01-.5 0v-2a.75.75 0 00-1.5 0v5a.75.75 0 00.75.75zM17.75 16a1.752 1.752 0 001.75 1.75h1a.75.75 0 000-1.5h-1a.25.25 0 01-.25-.25v-4a.75.75 0 00-1.5 0zM13 17.75a.75.75 0 00.75-.75v-2.085a.057.057 0 01.106-.029.781.781 0 001.288 0 .057.057 0 01.106.029V17a.75.75 0 001.5 0v-5a.751.751 0 00-1.394-.386l-.642 1.071a.25.25 0 01-.428 0l-.642-1.071A.751.751 0 0012.25 12v5a.75.75 0 00.75.75z"/></svg>',
},
attributes: {
id: {
type: String,
title: 'ID',
widget: 'input-text',
default: '',
},
class: {
type: String,
title: 'Class',
widget: 'input-text',
default: '',
},
style: {
type: String,
title: 'Style',
widget: 'input-text',
default: '',
},
},
titlebar({ attributes }) {
return []
.concat([
attributes.id ? `id: <strong>${attributes.id}</strong>` : null,
attributes.class ? `class: <strong>${attributes.class}</strong>` : null,
attributes.style ? `style: <strong>${attributes.style}</strong>` : null,
])
.filter((item) => !!item)
.join(', ');
},
content({ attributes }) {
const id = attributes.id || '';
const cclass = attributes.class || '';
const style = attributes.style || '';
return `<div id="${id}" class="${cclass}" style="${style}">{{content_editable}}</div>`;
},
});
@@ -0,0 +1,46 @@
window.nextgenEditor.addShortcode('figure', {
type: 'block',
plugin: 'shortcode-core',
title: 'Figure',
button: {
group: 'shortcode-core',
label: 'Figure',
icon: '<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24"><path d="M24 3a3 3 0 00-3-3H3a3 3 0 00-3 3v18a3 3 0 003 3h18a3 3 0 003-3zm-2 18a1 1 0 01-1 1H3a1 1 0 01-1-1V3a1 1 0 011-1h18a1 1 0 011 1z"/><circle cx="14" cy="9.5" r="3"/><path d="M14 5.25a.75.75 0 00.75-.75V4a.75.75 0 00-1.5 0v.5a.75.75 0 00.75.75zM9.935 6.494A.75.75 0 1011 5.434l-.353-.354a.75.75 0 00-1.066 1.061zM8.5 10.25H9a.75.75 0 000-1.5h-.5a.75.75 0 000 1.5zM18.065 12.506a.75.75 0 00-1.06 1.06l.353.354a.75.75 0 001.061-1.061zM18.25 9.5a.75.75 0 00.75.75h.5a.75.75 0 000-1.5H19a.75.75 0 00-.75.75zM17.535 6.715a.743.743 0 00.53-.221l.354-.353a.75.75 0 00-1.061-1.061l-.353.354a.751.751 0 00.53 1.281zM15.8 16.086a4.573 4.573 0 00-1.449.234.249.249 0 00-.12.388 7.827 7.827 0 011.518 3.654.161.161 0 00.159.138h3.154a1.536 1.536 0 001.264-.663 4.607 4.607 0 00-4.526-3.751zM7.914 14.551a6.875 6.875 0 00-4.32 1.518.25.25 0 00-.094.2v2.7A1.535 1.535 0 005.035 20.5h9.427a.251.251 0 00.193-.09.249.249 0 00.053-.205 6.909 6.909 0 00-6.794-5.654z"/></svg>',
},
attributes: {
id: {
type: String,
title: 'ID',
widget: 'input-text',
default: '',
},
class: {
type: String,
title: 'Class',
widget: 'input-text',
default: '',
},
caption: {
type: String,
title: 'Caption',
widget: 'input-text',
default: '',
},
},
titlebar({attributes }) {
return []
.concat([
attributes.id ? `id: <strong>${attributes.id}</strong>` : null,
attributes.class ? `class: <strong>${attributes.class}</strong>` : null,
])
.filter((item) => !!item)
.join(', ');
},
content({ attributes }) {
const id = attributes.id || '';
const cclass = attributes.class || '';
const caption = attributes.caption || '';
return `<div id="${id}" class="${cclass}">{{content_editable}}<div style="margin:0 8px;">${caption}</div></div>`;
},
});
@@ -0,0 +1,50 @@
window.nextgenEditor.addShortcode('fa', {
type: 'inline',
plugin: 'shortcode-core',
title: 'Font Awesome',
wrapOnInsert: false,
button: {
group: 'shortcode-core',
label: 'Font Awesome',
icon: '<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24"><path d="M11.093 18.527a1.5 1.5 0 01-.65.382.25.25 0 00-.181.212l-.227 1.941a1.03 1.03 0 001.752.849l2.671-2.671a7.688 7.688 0 001.622-2.446 12.4 12.4 0 00.366-3.007.25.25 0 00-.427-.186zM5.484 12.92l4.952-4.964a.251.251 0 00-.184-.427 12.988 12.988 0 00-3.087.349A7.687 7.687 0 004.75 9.531l-2.662 2.662a1.031 1.031 0 00.727 1.759c.035 0 1.572-.185 2.091-.248a.251.251 0 00.209-.174 1.5 1.5 0 01.369-.61zM6.038 16.536c-.845-.847-2.125-.7-3.183.353-.749.75-1.519 3.166-2.033 5.062a1 1 0 001.23 1.226c1.889-.52 4.3-1.3 5.046-2.045 1.057-1.057 1.2-2.337.354-3.182zM22.62.8c-1.248.252-3.756.838-4.534 1.616-.648.643-9.961 9.984-11.364 11.384a.25.25 0 000 .353l3.134 3.137a.25.25 0 00.353 0L21.587 5.913c.779-.779 1.365-3.287 1.616-4.534A.495.495 0 0022.62.8z"/></svg>',
},
attributes: {
icon: {
type: String,
title: 'Icon',
bbcode: true,
widget: 'input-text',
default: 'grav',
},
extras: {
type: String,
title: 'Extras',
widget: 'input-text',
default: '',
},
},
content({ attributes }) {
let faclass = 'fa';
let icon = attributes.icon && !attributes.icon.startsWith('fa-')
? `fa-${attributes.icon}`
: attributes.icon;
if (attributes.extras) {
attributes.extras.split(',').forEach((extra) => {
if (extra) {
if (['fab', 'fal', 'fas', 'far', 'fad'].includes(extra)) {
faclass = extra;
return;
}
icon += !extra.startsWith('fa-')
? ` fa-${extra}`
: ` ${extra}`;
}
});
}
return `<span class="${faclass} ${icon}" style="margin:4px"></span>`;
},
});
@@ -0,0 +1,32 @@
shortcode-block[name="h1"] .sc-content,
shortcode-block[name="h2"] .sc-content,
shortcode-block[name="h3"] .sc-content,
shortcode-block[name="h4"] .sc-content,
shortcode-block[name="h5"] .sc-content,
shortcode-block[name="h6"] .sc-content {
font-weight: 700;
}
shortcode-block[name="h1"] .sc-content {
font-size: 30px;
}
shortcode-block[name="h2"] .sc-content {
font-size: 24px;
}
shortcode-block[name="h3"] .sc-content {
font-size: 20px;
}
shortcode-block[name="h4"] .sc-content {
font-size: 18px;
}
shortcode-block[name="h5"] .sc-content {
font-size: 16px;
}
shortcode-block[name="h6"] .sc-content {
font-size: 14px;
}
@@ -0,0 +1,47 @@
window.nextgenEditor.addHook('hookInit', () => {
window.nextgenEditor.addButtonGroup('shortcode-core-headers', {
icon: '<svg viewBox="0 0 24 24" xmlns="http://www.w3.org/2000/svg"><path d="M17.567 20.509h-.61a.274.274 0 01-.24-.17L10.62 2.5l-.01-.01c-.21-.6-.76-1-1.39-1H9.2c-.63 0-1.19.39-1.39.99L1.74 20.29v-.01c-.04.09-.13.16-.24.16H.9a.976.976 0 10-.08 1.95h3l-.01-.001c.54 0 .97-.44.98-.98v-.02a.96.96 0 00-.82-.96l-.01-.001c-.07-.02-.14-.06-.17-.12a.245.245 0 01-.03-.2l1.5-4.413h-.01c.03-.1.12-.17.23-.17h7.23l-.01-.001c.1 0 .19.06.23.16l1.5 4.41c.04.12-.03.26-.16.31h-.04c-.47.07-.8.48-.8.95v-.01c-.01.54.43.97.97.98h2.94c.54.01.99-.41 1.01-.95.01-.55-.41-1-.95-1.02-.03-.01-.05-.01-.07-.01zM6.47 13.669v-.001c-.14 0-.25-.11-.25-.25-.01-.03 0-.06.01-.08L9 5.178h-.01c.04-.13.18-.2.31-.16.07.02.12.08.15.15l2.78 8.153c.02.07.01.15-.04.22h-.01c-.05.06-.13.1-.2.09z"/><path d="M23.02 20.509h-.22l-.01-.001a.274.274 0 01-.24-.17L18.29 7.87a1.53 1.53 0 00-1.94-.97c-.46.15-.81.5-.97.96l-1.15 3.38h-.01c-.18.51.09 1.06.61 1.24.51.17 1.06-.1 1.24-.62l.51-1.513v-.01c.04-.13.18-.2.31-.16.07.02.12.08.15.15l1.46 4.3c.04.12-.03.26-.16.31-.03 0-.06.01-.09.01h-1.37v-.01c-.55.01-.97.46-.95 1.01.01.51.43.93.94.94h2.2l-.01-.001c.1 0 .19.06.23.16l1.1 3.21a.25.25 0 01-.12.3v-.01c-.32.16-.52.49-.52.84v-.01c-.01.54.43.97.97.98h2.17c.54.01.99-.41 1.01-.95.01-.55-.41-1-.95-1.02-.03-.01-.05-.01-.07-.01z"/></svg>',
label: 'SC Headers',
});
});
for (let i = 1; i <= 6; i += 1) {
window.nextgenEditor.addShortcode(`h${i}`, {
type: 'block',
plugin: 'shortcode-core',
title: `H${i}`,
button: {
group: 'shortcode-core-headers',
label: `H${i}`,
},
attributes: {
id: {
type: String,
title: 'ID',
widget: 'input-text',
default: '',
},
class: {
type: String,
title: 'Class',
widget: 'input-text',
default: '',
},
},
titlebar({ attributes }) {
return []
.concat([
attributes.id ? `id: <strong>${attributes.id}</strong>` : null,
attributes.class ? `class: <strong>${attributes.class}</strong>` : null,
])
.filter((item) => !!item)
.join(', ');
},
content({ attributes }) {
const id = attributes.id || '';
const cclass = attributes.class || '';
return `<div id="${id}" class="${cclass}">{{content_editable}}</div>`;
},
});
}
@@ -0,0 +1,25 @@
window.nextgenEditor.addShortcode('lang', {
type: 'block',
plugin: 'shortcode-core',
title: 'Language',
button: {
group: 'shortcode-core',
label: 'Language',
icon: '<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24"><path d="M22.917 11H15.5a.5.5 0 00-.5.5v.417A3.083 3.083 0 0111.917 15H11.5a.5.5 0 00-.5.5v7.417A1.083 1.083 0 0012.083 24h10.834A1.083 1.083 0 0024 22.915V12.081A1.083 1.083 0 0022.917 11zm-2.153 11.2a.741.741 0 01-.264.048.749.749 0 01-.7-.486l-.507-1.352a.251.251 0 00-.234-.162h-3.116a.251.251 0 00-.234.162l-.509 1.352a.75.75 0 01-1.4-.528l2.532-6.751a1.25 1.25 0 012.34 0l1.758 4.687a.889.889 0 01.038.1l.736 1.963a.75.75 0 01-.44.967z"/><path d="M16.459 18.41a.25.25 0 00.234.338h1.614a.25.25 0 00.234-.338l-.807-2.151a.25.25 0 00-.468 0zM7.779 5.607a.251.251 0 00-.226-.359H5.447a.251.251 0 00-.226.359 7.962 7.962 0 001.088 1.667.249.249 0 00.382 0 7.962 7.962 0 001.088-1.667z"/><path d="M11.917 13A1.083 1.083 0 0013 11.915V1.081A1.083 1.083 0 0011.917 0H1.083A1.083 1.083 0 000 1.081v10.834A1.083 1.083 0 001.083 13zm-1.193-2.3a.751.751 0 01-.724.554.782.782 0 01-.2-.026A9.212 9.212 0 016.651 9.67a.249.249 0 00-.3 0A9.212 9.212 0 013.2 11.222a.782.782 0 01-.2.026.749.749 0 01-.2-1.473 7.707 7.707 0 002.365-1.1.253.253 0 00.11-.175.248.248 0 00-.058-.2A9.508 9.508 0 013.53 5.412a.249.249 0 00-.23-.164h-.769a.75.75 0 010-1.5H5.5a.25.25 0 00.25-.25v-1a.75.75 0 111.5 0v1a.25.25 0 00.25.25h3a.75.75 0 010 1.5h-.795a.249.249 0 00-.235.164A9.508 9.508 0 017.783 8.3a.25.25 0 00.048.368 7.707 7.707 0 002.365 1.1.749.749 0 01.528.926zM17.646 5.352A.5.5 0 0018.5 5v-.31a.25.25 0 01.367-.221A4 4 0 0121 8a1 1 0 102 0 6 6 0 00-4.32-5.753.25.25 0 01-.18-.24V1a.5.5 0 00-.309-.462.506.506 0 00-.545.109l-2 2a.5.5 0 000 .707zM2 14a1 1 0 00-1 .992V15a6 6 0 004.32 5.753.25.25 0 01.18.24V22a.5.5 0 00.854.354l2-2a.5.5 0 000-.707l-2-2A.5.5 0 005.5 18v.31a.252.252 0 01-.121.215.248.248 0 01-.246.006A4 4 0 013 15a1 1 0 00-1-1z"/></svg>',
},
attributes: {
lang: {
type: String,
title: 'Language',
bbcode: true,
widget: 'input-text',
default: 'en',
},
},
titlebar({ attributes }) {
return `language: <strong>${attributes.lang}</strong>`;
},
content() {
return '{{content_editable}}';
},
});
@@ -0,0 +1,80 @@
const sentence = 'Lorem ipsum dolor sit amet consectetur adipiscing elit, molestie tortor cubilia eu facilisi ex varius, convallis pretium dapibus fusce porta ligula.';
const words = [].concat(...Array(1000).fill(sentence.toLowerCase().replace(/[.|,]/g, '').split(' ')));
const paragraph = Array(2).fill(sentence).join(' ');
window.nextgenEditor.addShortcode('lorem', {
type: 'block',
plugin: 'shortcode-core',
title: 'Lorem',
wrapOnInsert: false,
button: {
group: 'shortcode-core',
label: 'Lorem',
icon: '<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24"><path d="M7.54 9a.48.48 0 00.172-.031A14.327 14.327 0 0112 8a14.327 14.327 0 014.288.969.507.507 0 00.172.031H19a.454.454 0 00.394-.678 8.553 8.553 0 00-4.206-3.685.5.5 0 00-.688.463v.4a.5.5 0 01-1 0v-4a1.5 1.5 0 00-3 0v4a.5.5 0 01-1 0v-.4a.5.5 0 00-.688-.463 8.555 8.555 0 00-4.206 3.684A.454.454 0 005 9zM20.5 12a1.5 1.5 0 00-1.5-1.5h-2.813a.493.493 0 01-.178-.033A14 14 0 0012 9.5a14 14 0 00-4.009.967.493.493 0 01-.178.033H5A1.5 1.5 0 003.5 12v6.639a3.5 3.5 0 001.2 2.633l2.87 2.512A.866.866 0 009 23.136V17a1.5 1.5 0 00-1.5-1.5H6.25a.75.75 0 010-1.5H9a1.5 1.5 0 011.5 1.5v2.793a.993.993 0 00.293.707l.5.5a1 1 0 001.414 0l.5-.5a.993.993 0 00.293-.707V15.5A1.5 1.5 0 0115 14h2.75a.75.75 0 010 1.5H16.5A1.5 1.5 0 0015 17v6.137a.864.864 0 001.432.649l2.873-2.514a3.5 3.5 0 001.2-2.633z"/></svg>',
},
attributes: {
p: {
type: Number,
title: 'Paragraphs',
bbcode: true,
widget: {
type: 'input-number',
min: 0,
max: 10,
},
default: 2,
},
tag: {
type: String,
title: 'Tag',
widget: 'input-text',
default: 'p',
},
s: {
type: Number,
title: 'Sentences',
widget: 'input-number',
default: 0,
},
w: {
type: Number,
title: 'Words',
widget: 'input-number',
default: 0,
},
},
titlebar({ attributes }) {
if (attributes.w) {
return `words: <strong>${attributes.w}</strong>`;
}
if (attributes.s) {
return `sentences: <strong>${attributes.s}</strong>`;
}
if (attributes.p) {
return `paragraphs: <strong>${attributes.p}</strong>`;
}
return '';
},
content({ attributes }) {
let output = '';
output += '<div style="margin:16px 16px">';
if (attributes.w) {
output += words.slice(0, attributes.w).join(' ');
} else if (attributes.s) {
output += Array(attributes.s).fill(sentence).join(' ');
} else if (attributes.p) {
[...Array(attributes.p)].forEach(() => {
output += `<p>${paragraph}</p>`;
});
}
output += '</div>';
return output;
},
});
@@ -0,0 +1,7 @@
shortcode-inline[name="mark"] > .sc-content > span {
background: #ffe9b3;
border-bottom: .05rem solid #ffd367;
border-radius: .1rem;
color: #50596c;
padding: .05rem .1rem 0;
}
@@ -0,0 +1,49 @@
window.nextgenEditor.addShortcode('mark', {
type: 'inline',
plugin: 'shortcode-core',
title: 'Mark',
button: {
group: 'shortcode-core',
label: 'Mark',
icon: '<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24"><path d="M3.448 18a.253.253 0 00-.184-.073.25.25 0 00-.179.083L.192 21.247A.75.75 0 00.751 22.5H4a.752.752 0 00.507-.2L6 20.929a.244.244 0 00.081-.178.25.25 0 00-.073-.183zM7.27 20.035a1.256 1.256 0 001.7.068c.611-.524 1.8-1.278 2.894-.447a1.269 1.269 0 001.7-.171l.182-.227a.25.25 0 00-.018-.333l-8.673-8.667a.249.249 0 00-.341-.011l-.273.238a1.257 1.257 0 00-.111 1.641c.832 1.094.078 2.282-.444 2.894a1.254 1.254 0 00.065 1.7zM14.312 18.1a.249.249 0 00.372-.021L23.1 7.6a1.884 1.884 0 00-.133-2.486L18.379.523A1.841 1.841 0 0015.9.443L5.844 9.256a.25.25 0 00-.012.365zM24 23a1 1 0 00-1-1H9a1 1 0 000 2h14a1 1 0 001-1z"/></svg>',
},
attributes: {
style: {
type: String,
title: 'Style',
bbcode: true,
widget: {
type: 'radios',
values: [
{ value: 'inline', label: 'Inline' },
{ value: 'block', label: 'Block' },
],
},
default: 'inline',
},
class: {
type: String,
title: 'Class',
widget: 'input-text',
default: '',
},
},
titlebar({ attributes }) {
return []
.concat([
attributes.style ? `style: <strong>${attributes.style}</strong>` : null,
attributes.class ? `class: <strong>${attributes.class}</strong>` : null,
])
.filter((item) => !!item)
.join(', ');
},
content({ attributes }) {
const style = attributes.style === 'block'
? 'display:block'
: '';
const cclass = `mark-class-${attributes.class}`;
return `<span class="${cclass}" style="${style}">{{content_editable}}</span>`;
},
});
@@ -0,0 +1,63 @@
shortcode-block[name="notice"] .sc-notice {
color: #666;
font-size: 16px;
line-height: 24px;
margin: 8px 8px;
position: relative;
}
shortcode-block[name="notice"] .sc-notice .sc-notice-wrapper {
padding: 4px 12px;
}
shortcode-block[name="notice"] .sc-notice .sc-notice-wrapper:before {
color: rgb(255, 255, 255);
content: "";
font-family: FontAwesome;
left: 10px;
position: absolute;
top: 2px;
}
shortcode-block[name="notice"] .sc-notice .sc-notice-wrapper:after {
color: #fff;
left: 30px;
position: absolute;
top: 3px;
}
shortcode-block[name="notice"] .sc-notice-info .sc-notice-wrapper {
border-top: 30px solid #F0B37E;
background: #FFF2DB;
}
shortcode-block[name="notice"] .sc-notice-warning .sc-notice-wrapper {
border-top: 30px solid #DF6F6C;
background: #FAE2E2;
}
shortcode-block[name="notice"] .sc-notice-note .sc-notice-wrapper {
border-top: 30px solid #6AB0DE;
background: #E7F2FA;
}
shortcode-block[name="notice"] .sc-notice-tip .sc-notice-wrapper {
border-top: 30px solid #77C577;
background: #E6F9E6;
}
shortcode-block[name="notice"] .sc-notice-info .sc-notice-wrapper:after {
content: 'Info';
}
shortcode-block[name="notice"] .sc-notice-warning .sc-notice-wrapper:after {
content: 'Warning';
}
shortcode-block[name="notice"] .sc-notice-note .sc-notice-wrapper:after {
content: 'Note';
}
shortcode-block[name="notice"] .sc-notice-tip .sc-notice-wrapper:after {
content: 'Tip';
}
@@ -0,0 +1,41 @@
window.nextgenEditor.addShortcode('notice', {
type: 'block',
plugin: 'shortcode-core',
title: 'Notice',
button: {
group: 'shortcode-core',
label: 'Notice',
icon: '<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24"><path d="M8.5 14a1 1 0 00-.665.252L5 16.773V15a1 1 0 00-1-1H2.25a.251.251 0 01-.25-.253V2.25A.249.249 0 012.251 2h18a.25.25 0 01.25.25v10.007a.248.248 0 00.028.116l1.316 2.509a.25.25 0 00.445 0A1.939 1.939 0 0022.5 14V2a2 2 0 00-2-2H2a2 2 0 00-2 2v12.053A1.953 1.953 0 002 16h1v3a1 1 0 001.664.748L8.881 16h3.537a.251.251 0 00.221-.134l.787-1.5a.249.249 0 00-.007-.245.252.252 0 00-.214-.121z"/><path d="M18.782 12.271a1.45 1.45 0 00-2.562 0l-5.055 9.634a1.433 1.433 0 00.048 1.409 1.457 1.457 0 001.232.686h10.111a1.459 1.459 0 001.234-.687 1.434 1.434 0 00.047-1.408zM17.5 15.25a.75.75 0 01.75.75v3a.75.75 0 01-1.5 0v-3a.75.75 0 01.75-.75zm0 7a1 1 0 111-1 1 1 0 01-1 1z"/></svg>',
},
attributes: {
notice: {
type: String,
title: 'Type',
bbcode: true,
widget: {
type: 'radios',
values: [
{ value: 'info', label: 'Info' },
{ value: 'warning', label: 'Warning' },
{ value: 'note', label: 'Note' },
{ value: 'tip', label: 'Tip' },
],
},
default: 'info',
},
},
titlebar({ attributes }) {
const notice = attributes.notice
? this.attributes.notice.widget.values.find((item) => item.value === attributes.notice)
: '';
const type = notice
? notice.label
: '';
return `type: <strong>${type}</strong>`;
},
content({ attributes }) {
return `<div class="sc-notice sc-notice-${attributes.notice}"><div class="sc-notice-wrapper">{{content_editable}}</div></div>`;
},
});
@@ -0,0 +1,13 @@
window.nextgenEditor.addShortcode('raw', {
type: 'block',
plugin: 'shortcode-core',
title: 'Raw',
button: {
group: 'shortcode-core',
label: 'Raw',
icon: '<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 15.034 9"><path d="M5.726 0a.5.5 0 00-.5.5h-2.25a2.744 2.744 0 00-1.807 4.813A1.998 1.998 0 00.226 7c0 1.1.9 2 2 2h8c1.1 0 2-.9 2-2 0-.488-.186-.93-.48-1.277l2.177.963a.75.75 0 10.606-1.372l-1.81-.802 1.63-.272a.75.75 0 10-.246-1.48l-2.13.355C11.484 1.952 10.264.784 8.226.55V.5a.5.5 0 00-.5-.5h-2zm.5 1h1v7h-1V1zm3.5 4c.259 0 .464.197.49.45l.076-.134a.5.5 0 11.866.5l-.258.448a.986.986 0 01.326.736c0 .563-.437 1-1 1h-2V6h1v-.5c0-.277.223-.5.5-.5zm-7.06.07a.498.498 0 01.494.246l.2.348a.493.493 0 01.366-.164c.277 0 .5.223.5.5h1v2h-3c-.563 0-1-.437-1-1s.437-1 1-1H2.4l-.106-.184a.497.497 0 01.371-.746z"/></svg>',
},
content() {
return '{{content_editable}}';
},
});
@@ -0,0 +1,54 @@
window.nextgenEditor.addShortcode('safe-email', {
type: 'inline',
plugin: 'shortcode-core',
title: 'Safe Email',
button: {
group: 'shortcode-core',
label: 'Safe Email',
icon: '<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24"><path d="M19 9.25a4.924 4.924 0 011.666.291.25.25 0 00.334-.236V1.75a.158.158 0 00-.1-.147.16.16 0 00-.173.034L12.2 10.164a2.407 2.407 0 01-3.4 0L.271 1.637A.159.159 0 000 1.75v10.5A1.749 1.749 0 001.75 14h12.043a.25.25 0 00.249-.226A4.992 4.992 0 0119 9.25z"/><path d="M9.726 9.236a1.094 1.094 0 001.547 0L19.748.761A.437.437 0 0019.5.019 1.62 1.62 0 0019.249 0h-17.5A1.62 1.62 0 001.5.019a.437.437 0 00-.352.3.441.441 0 00.102.442zM22.5 15.5v-1.25a3.5 3.5 0 00-7 0v1.25A1.5 1.5 0 0014 17v5.5a1.5 1.5 0 001.5 1.5h7a1.5 1.5 0 001.5-1.5V17a1.5 1.5 0 00-1.5-1.5zM19 12.75a1.5 1.5 0 011.5 1.5v1.25h-3v-1.25a1.5 1.5 0 011.5-1.5zm1 7.5a1 1 0 11-1-1 1 1 0 011 1z"/></svg>',
},
attributes: {
subject: {
type: String,
title: 'Subject',
widget: 'input-text',
default: '',
},
icon: {
type: String,
title: 'Icon',
bbcode: true,
widget: 'input-text',
default: 'grav',
},
autolink: {
type: String,
title: 'Autolink',
widget: {
type: 'checkbox',
valueType: String,
label: 'Yes',
},
default: 'false',
},
},
content({ attributes }) {
let output = '';
if (attributes.autolink === 'true') {
output += '<span style="color:#1c90fb">';
}
if (attributes.icon) {
output += `<span class="fa fa-${attributes.icon}" style="margin-left:4px"></span>`;
}
output += '{{content_editable}}';
if (attributes.autolink === 'true') {
output += '</span>';
}
return output;
},
});
@@ -0,0 +1,26 @@
window.nextgenEditor.addShortcode('section', {
type: 'block',
plugin: 'shortcode-core',
title: 'Section',
button: {
group: 'shortcode-core',
label: 'Section',
icon: '<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24"><path d="M20.242 18.827a6.523 6.523 0 10-1.414 1.414l3.465 3.465a1.014 1.014 0 001.414 0 1 1 0 000-1.414zM15 10.5a4.5 4.5 0 11-4.5 4.5 4.505 4.505 0 014.5-4.5z"/><path d="M13 15.749h1.25V17a.75.75 0 001.5 0v-1.25H17a.75.75 0 000-1.5h-1.25V13a.75.75 0 00-1.5 0v1.25H13a.75.75 0 000 1.5zM3.933 0H1.957A1.959 1.959 0 000 1.956v1.977a1 1 0 002 0L1.957 2h1.976a1 1 0 000-2zM3.933 22L2 22.042v-1.976a1 1 0 00-2 0v1.976A1.959 1.959 0 001.957 24h1.976a1 1 0 000-2zM1 11.533a1 1 0 001-1V7.6a1 1 0 00-2 0v2.934a1 1 0 001 .999zM1 17.4a1 1 0 001-1v-2.934a1 1 0 00-2 0V16.4a1 1 0 001 1zM23 6.6a1 1 0 00-1 1v2.934a1 1 0 102 0V7.6a1 1 0 00-1-1zM7.6 2H10a1 1 0 000-2H7.6a1 1 0 000 2zM14 2h2.4a1 1 0 000-2H14a1 1 0 000 2zM20.067 2L22 1.956v1.977a1 1 0 002 0V1.956A1.959 1.959 0 0022.043 0h-1.976a1 1 0 000 2zM10.533 22H7.6a1 1 0 100 2h2.933a1 1 0 000-2z"/></svg>',
},
attributes: {
name: {
type: String,
title: 'Name',
widget: 'input-text',
default: '',
},
},
titlebar({ attributes }) {
return attributes.name
? `name: <strong>${attributes.name}</strong>`
: '';
},
content() {
return '{{content_editable}}';
},
});
@@ -0,0 +1,10 @@
window.nextgenEditor.addHook('hookInit', () => {
window.nextgenEditor.addShortcodePlugin('shortcode-core', {
title: 'Shortcode Core',
});
window.nextgenEditor.addButtonGroup('shortcode-core', {
icon: '<svg viewBox="0 0 24 24" xmlns="http://www.w3.org/2000/svg"><path d="M22 0H1.99c-1.11 0-2 .89-2 2v7-.01c-.01 1.1.89 2 1.99 2h20l-.01-.001c1.1 0 2-.9 2-2v-7a2 2 0 00-2-2zm-7.25 8.5c0 .27-.23.5-.5.5H2.49a.51.51 0 01-.5-.51V2.479c0-.28.22-.5.5-.5h11.75-.01c.27-.01.5.22.5.49zM21 6.85h-.01c-.01.4-.33.72-.73.72a.824.824 0 01-.46-.16l-1.75-1.4-.01-.01a.733.733 0 01-.12-1.03c.03-.05.07-.09.11-.12l1.74-1.4h-.01c.31-.26.77-.21 1.02.11.1.13.16.29.15.46z"/><path d="M4 4.75h7.5l-.01-.001a.749.749 0 100-1.5H3.98c-.42 0-.75.33-.75.75 0 .41.33.75.75.75zM4 7.75h4.5l-.01-.001a.749.749 0 100-1.5H3.98c-.42 0-.75.33-.75.75 0 .41.33.75.75.75zM22 13H1.99c-1.11 0-2 .89-2 2v7-.01c-.01 1.1.89 2 1.99 2h20l-.01-.001c1.1 0 2-.9 2-2v-7a2 2 0 00-2-2zm-7.25 8.5c0 .27-.23.5-.5.5H2.49a.51.51 0 01-.5-.51v-6c-.01-.28.22-.51.49-.51h11.75-.01c.27-.01.5.22.5.49zM21 19.85h-.01c-.01.4-.33.72-.73.72a.824.824 0 01-.46-.16l-1.75-1.4-.01-.01a.733.733 0 01-.12-1.03c.03-.05.07-.09.11-.12l1.74-1.4h-.01c.31-.26.77-.21 1.02.11.1.13.16.29.15.46z"/><path d="M4 17.75h7.5-.01a.749.749 0 100-1.5H3.98c-.42 0-.75.33-.75.75 0 .41.33.75.75.75zM4 20.75h4.5-.01a.749.749 0 100-1.5H3.98c-.42 0-.75.33-.75.75 0 .41.33.75.75.75z"/></svg>',
label: 'Shortcode Core',
});
});
@@ -0,0 +1,26 @@
window.nextgenEditor.addShortcode('size', {
type: 'inline',
plugin: 'shortcode-core',
title: 'Font Size',
button: {
group: 'shortcode-core',
label: 'Font Size',
icon: '<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24"><path d="M13 3.993H2a2 2 0 00-2 2v2a1 1 0 002 0v-1.75a.249.249 0 01.25-.25h4a.249.249 0 01.25.25v12.5a.25.25 0 01-.25.25H4.5a1 1 0 000 2h6a1 1 0 000-2H8.75a.25.25 0 01-.25-.25v-12.5a.249.249 0 01.25-.25h4a.249.249 0 01.25.25v1.75a1 1 0 102 0v-2a2 2 0 00-2-2zM23.5 18.493h-1.75a.25.25 0 01-.25-.25v-12.5a.249.249 0 01.25-.25h1.75a.5.5 0 00.4-.8l-3-4a.518.518 0 00-.8 0l-3 4a.5.5 0 00.4.8h1.75a.249.249 0 01.25.25v12.5a.25.25 0 01-.25.25H17.5a.5.5 0 00-.4.8l3 4a.5.5 0 00.8 0l3-4a.5.5 0 00-.4-.8z"/></svg>',
},
attributes: {
size: {
type: String,
title: 'Size',
bbcode: true,
widget: 'input-text',
default: '14',
},
},
content({ attributes }) {
const size = !Number.isNaN(+attributes.size)
? `${attributes.size}px`
: attributes.size;
return `<span style="font-size:${size}">{{content_editable}}</span>`;
},
});
@@ -0,0 +1,37 @@
window.nextgenEditor.addShortcode('span', {
type: 'inline',
plugin: 'shortcode-core',
title: 'Span',
button: {
group: 'shortcode-core',
label: 'Span',
icon: '<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24"><path d="M24 4.5a3 3 0 00-3-3H3a3 3 0 00-3 3v15a3 3 0 003 3h18a3 3 0 003-3zM3 5a1 1 0 111 1 1 1 0 01-1-1zm3 0a1 1 0 111 1 1 1 0 01-1-1zm3 0a1 1 0 111 1 1 1 0 01-1-1zm13 14.5a1 1 0 01-1 1H3a1 1 0 01-1-1V9a.5.5 0 01.5-.5h19a.5.5 0 01.5.5z"/><path d="M7.75 12a.75.75 0 00.75.75.25.25 0 01.25.25v4a.75.75 0 001.5 0v-4a.25.25 0 01.25-.25.75.75 0 000-1.5h-2a.75.75 0 00-.75.75zM4 17.75a.75.75 0 00.75-.75v-1a.25.25 0 01.5 0v1a.75.75 0 001.5 0v-5a.75.75 0 00-1.5 0v2a.25.25 0 01-.5 0v-2a.75.75 0 00-1.5 0v5a.75.75 0 00.75.75zM17.75 16a1.752 1.752 0 001.75 1.75h1a.75.75 0 000-1.5h-1a.25.25 0 01-.25-.25v-4a.75.75 0 00-1.5 0zM13 17.75a.75.75 0 00.75-.75v-2.085a.057.057 0 01.106-.029.781.781 0 001.288 0 .057.057 0 01.106.029V17a.75.75 0 001.5 0v-5a.751.751 0 00-1.394-.386l-.642 1.071a.25.25 0 01-.428 0l-.642-1.071A.751.751 0 0012.25 12v5a.75.75 0 00.75.75z"/></svg>',
},
attributes: {
id: {
type: String,
title: 'ID',
widget: 'input-text',
default: '',
},
class: {
type: String,
title: 'Class',
widget: 'input-text',
default: '',
},
style: {
type: String,
title: 'Style',
widget: 'input-text',
default: '',
},
},
content({ attributes }) {
const id = attributes.id || '';
const cclass = attributes.class || '';
const style = attributes.style || '';
return `<span id="${id}" class="${cclass}" style="${style}">{{content_editable}}</span>`;
},
});
@@ -0,0 +1,13 @@
window.nextgenEditor.addShortcode('u', {
type: 'inline',
plugin: 'shortcode-core',
title: 'Underline',
button: {
group: 'shortcode-core',
label: 'Underline',
icon: '<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24"><path d="M22.5 21.248h-21a1.25 1.25 0 000 2.5h21a1.25 1.25 0 000-2.5zM1.978 2.748h1.363a.25.25 0 01.25.25v8.523a8.409 8.409 0 0016.818 0V3a.25.25 0 01.25-.25h1.363a1.25 1.25 0 000-2.5H16.3a1.25 1.25 0 000 2.5h1.363a.25.25 0 01.25.25v8.523a5.909 5.909 0 01-11.818 0V3a.25.25 0 01.25-.25H7.7a1.25 1.25 0 100-2.5H1.978a1.25 1.25 0 000 2.5z"/></svg>',
},
content() {
return '<span style="text-decoration:underline">{{content_editable}}</span>';
},
});
@@ -0,0 +1,30 @@
export default function collapse(input) {
let output = input;
output = output.replace(/<figure class="image">((((?!(<\/figure>)).)|\n)*)<\/figure>/gm, '$1');
const domOutput = new DOMParser().parseFromString(output, 'text/html');
[...domOutput.querySelectorAll('shortcode-block, shortcode-inline')].forEach((domShortcode) => {
domShortcode.setAttribute('sc-rendered', false);
});
let domShortcode = domOutput.querySelector('shortcode-block[sc-rendered], shortcode-inline[sc-rendered]');
while (domShortcode) {
const name = domShortcode.getAttribute('name');
const shortcode = window.nextgenEditor.shortcodes[name];
domShortcode.removeAttribute('class');
domShortcode.removeAttribute('sc-rendered');
const domInnerContent = domShortcode.querySelector(`shortcode-${shortcode.type}-editable, shortcode-${shortcode.type}-readonly`);
domShortcode.innerHTML = (domInnerContent && domInnerContent.innerHTML) || '';
domShortcode = domOutput.querySelector('shortcode-block[sc-rendered], shortcode-inline[sc-rendered]');
}
output = domOutput.body.innerHTML;
return output;
}
@@ -0,0 +1,153 @@
import collapse from './collapse';
import uncollapse from './uncollapse';
const Command = window.nextgenEditor.classes.core.command.class;
window.nextgenEditor.addPlugin('GravShortcodeCoreCommand', {
init() {
Object.values(window.nextgenEditor.shortcodes).forEach((shortcode) => {
const commandName = `shortcode_${shortcode.name}`;
class GravShortcodeCoreCommand extends Command {
execute(args) {
this.editor.model.change((modelWriter) => {
let dataShortcode = '';
const argsForUncollapse = {};
const wrapOnInsert = !shortcode.child && !shortcode.parent
? shortcode.wrapOnInsert !== undefined
? shortcode.wrapOnInsert
: true
: false;
const selectedBlocks = [...this.editor.model.document.selection.getSelectedBlocks()];
const selectedItems = [...this.editor.model.document.selection.getFirstRange().getItems({ shallow: true })];
const firstSelectedBlock = selectedBlocks[0];
const firstBlockSelectedItems = selectedItems.filter((item) => item.parent === firstSelectedBlock);
const attributes = Object.keys(shortcode.attributes).reduce((acc, attrName) => {
acc[attrName] = shortcode.attributes[attrName].default.value;
return acc;
}, {});
dataShortcode += `<shortcode-${shortcode.type} name="${shortcode.name}" attributes="${encodeURIComponent(JSON.stringify(attributes))}">`;
if (wrapOnInsert) {
if (shortcode.type === 'block') {
const modelSelectedBlocks = modelWriter.createDocumentFragment();
selectedBlocks.forEach((block) => modelWriter.append(modelWriter.cloneElement(block), modelSelectedBlocks));
const viewSelectedBlocks = this.editor.data.toView(modelSelectedBlocks);
const dataSelectedBlocks = this.editor.data.processor.toData(viewSelectedBlocks);
dataShortcode += collapse(dataSelectedBlocks);
}
if (shortcode.type === 'inline') {
const modelSelectedBlocks = modelWriter.createDocumentFragment();
firstBlockSelectedItems.forEach((item) => {
const block = item.textNode
? modelWriter.createText(item.data)
: modelWriter.cloneElement(item);
modelWriter.append(block, modelSelectedBlocks);
});
const viewSelectedBlocks = this.editor.data.toView(modelSelectedBlocks);
const dataSelectedBlocks = this.editor.data.processor.toData(viewSelectedBlocks);
dataShortcode += collapse(dataSelectedBlocks);
}
}
if (shortcode.parent) {
dataShortcode += '<p>&nbsp;</p>';
}
dataShortcode += `</shortcode-${shortcode.type}>`;
if (shortcode.parent) {
if (args && args.modelParentShortcode) {
argsForUncollapse.parentAttributes = JSON.parse(decodeURIComponent(args.modelParentShortcode.getAttribute('attributes')));
}
}
dataShortcode = uncollapse(dataShortcode, argsForUncollapse);
const convertContext = shortcode.type === 'inline'
? '$block'
: '$root';
const viewShortcode = this.editor.data.processor.toView(dataShortcode).getChild(0);
const modelShortcode = this.editor.data.toModel(viewShortcode, convertContext).getChild(0);
let insertPosition = modelWriter.createPositionAt(this.editor.model.document.getRoot(), 0);
if (!args || !args.insertPosition) {
if (shortcode.type === 'block') {
const firstBlock = selectedBlocks[0];
const lastBlock = selectedBlocks[selectedBlocks.length - 1];
if (wrapOnInsert) {
insertPosition = modelWriter.createPositionBefore(firstBlock);
modelWriter.remove(
modelWriter.createRange(
modelWriter.createPositionBefore(firstBlock),
modelWriter.createPositionAfter(lastBlock),
),
);
} else {
insertPosition = modelWriter.createPositionAfter(lastBlock);
if (lastBlock && lastBlock.name === 'paragraph' && lastBlock.childCount === 0) {
insertPosition = modelWriter.createPositionBefore(lastBlock);
modelWriter.remove(lastBlock);
}
}
}
if (shortcode.type === 'inline') {
const firstItem = firstBlockSelectedItems.length
? firstBlockSelectedItems[0]
: null;
const lastItem = firstBlockSelectedItems.length
? firstBlockSelectedItems[firstBlockSelectedItems.length - 1]
: null;
if (wrapOnInsert) {
insertPosition = firstItem
? modelWriter.createPositionBefore(firstItem)
: this.editor.model.document.selection.getFirstPosition();
if (firstItem) {
modelWriter.remove(
modelWriter.createRange(
modelWriter.createPositionBefore(firstItem),
modelWriter.createPositionAfter(lastItem),
),
);
}
} else {
insertPosition = lastItem
? modelWriter.createPositionAfter(lastItem)
: this.editor.model.document.selection.getFirstPosition();
}
}
} else {
insertPosition = args.insertPosition;
}
modelWriter.insert(modelShortcode, insertPosition);
modelWriter.setSelection(modelShortcode, 'on');
});
}
}
this.editor.commands.add(commandName, new GravShortcodeCoreCommand(this.editor));
});
},
});
@@ -0,0 +1,150 @@
const Widget = window.nextgenEditor.classes.widget.class;
const { toWidget, toWidgetEditable } = window.nextgenEditor.classes.widget.utils;
window.nextgenEditor.addPlugin('GravShortcodeCoreConvertersBlock', {
requires: [Widget],
init() {
this.editor.model.schema.register('shortcode-block', {
isBlock: true,
isObject: true,
allowWhere: '$block',
allowContentOf: '$root',
allowAttributes: [
'name',
'attributes',
'class',
],
});
this.editor.conversion.for('upcast').elementToElement({
view: 'shortcode-block',
model(viewElement, { writer }) {
return writer.createElement('shortcode-block', viewElement.getAttributes());
},
});
this.editor.conversion.for('dataDowncast').elementToElement({
model: 'shortcode-block',
view(modelElement, { writer }) {
return writer.createContainerElement('shortcode-block', modelElement.getAttributes());
},
});
this.editor.conversion.for('editingDowncast').elementToElement({
model: 'shortcode-block',
view(modelElement, { writer }) {
const container = writer.createContainerElement('shortcode-block', modelElement.getAttributes());
return toWidget(container, writer);
},
});
this.editor.model.schema.register('shortcode-block-editable', {
isLimit: true,
allowWhere: '$block',
allowContentOf: '$root',
});
this.editor.conversion.for('upcast').elementToElement({
view: 'shortcode-block-editable',
model: 'shortcode-block-editable',
});
this.editor.conversion.for('dataDowncast').elementToElement({
model: 'shortcode-block-editable',
view: 'shortcode-block-editable',
});
this.editor.conversion.for('editingDowncast').elementToElement({
model: 'shortcode-block-editable',
view(modelElement, { writer }) {
const container = writer.createEditableElement('shortcode-block-editable', modelElement.getAttributes());
return toWidgetEditable(container, writer);
},
});
this.editor.model.schema.register('shortcode-block-readonly', {
isLimit: true,
allowWhere: '$block',
allowContentOf: '$root',
});
this.editor.conversion.elementToElement({
view: 'shortcode-block-readonly',
model: 'shortcode-block-readonly',
});
},
});
window.nextgenEditor.addPlugin('GravShortcodeCoreConvertersInline', {
requires: [Widget],
init() {
this.editor.model.schema.register('shortcode-inline', {
isObject: true,
isInline: true,
allowWhere: '$text',
allowContentOf: '$block',
allowAttributes: [
'name',
'attributes',
'class',
],
});
this.editor.conversion.for('upcast').elementToElement({
view: 'shortcode-inline',
model(viewElement, { writer }) {
return writer.createElement('shortcode-inline', viewElement.getAttributes());
},
});
this.editor.conversion.for('dataDowncast').elementToElement({
model: 'shortcode-inline',
view(modelElement, { writer }) {
return writer.createContainerElement('shortcode-inline', modelElement.getAttributes());
},
});
this.editor.conversion.for('editingDowncast').elementToElement({
model: 'shortcode-inline',
view(modelElement, { writer }) {
const container = writer.createContainerElement('shortcode-inline', modelElement.getAttributes());
return toWidget(container, writer);
},
});
this.editor.model.schema.register('shortcode-inline-editable', {
isLimit: true,
allowWhere: '$text',
allowContentOf: '$block',
});
this.editor.conversion.for('upcast').elementToElement({
view: 'shortcode-inline-editable',
model: 'shortcode-inline-editable',
});
this.editor.conversion.for('dataDowncast').elementToElement({
model: 'shortcode-inline-editable',
view: 'shortcode-inline-editable',
});
this.editor.conversion.for('editingDowncast').elementToElement({
model: 'shortcode-inline-editable',
view(modelElement, { writer }) {
const container = writer.createEditableElement('shortcode-inline-editable', modelElement.getAttributes());
return toWidgetEditable(container, writer);
},
});
this.editor.model.schema.register('shortcode-inline-readonly', {
isLimit: true,
allowWhere: '$text',
allowContentOf: '$block',
});
this.editor.conversion.elementToElement({
view: 'shortcode-inline-readonly',
model: 'shortcode-inline-readonly',
});
},
});
@@ -0,0 +1,86 @@
import displaySettings from './settings';
window.scDisplaySettings = function scDisplaySettings() {
const domShortcode = this.closest('shortcode-block, shortcode-inline');
if (domShortcode) {
displaySettings(domShortcode);
}
};
window.scBlockAddChildFromParent = function scBlockAddChildFromParent() {
const { editors } = window.nextgenEditor;
const domShortcode = this.parentNode;
const editor = (editors.filter((instance) => instance.ui.view.element.contains(domShortcode)) || []).shift();
const name = domShortcode.getAttribute('name');
const shortcode = window.nextgenEditor.shortcodes[name];
if (editor) {
const viewShortcode = editor.editing.view.domConverter.mapDomToView(domShortcode);
const modelShortcode = editor.editing.mapper.toModelElement(viewShortcode);
const domShortcodeBlockReadOnly = domShortcode.querySelector('shortcode-block-readonly');
const viewShortcodeBlockReadOnly = editor.editing.view.domConverter.mapDomToView(domShortcodeBlockReadOnly);
const modelShortcodeBlockReadOnly = editor.editing.mapper.toModelElement(viewShortcodeBlockReadOnly);
editor.model.change((modelWriter) => {
const insertPosition = modelWriter.createPositionAt(modelShortcodeBlockReadOnly, 0);
editor.execute(`shortcode_${shortcode.child.name}`, { insertPosition, modelParentShortcode: modelShortcode });
domShortcode.querySelector('.sc-add-child').classList.remove('sc-visible');
});
}
};
window.scBlockAddChild = function scBlockAddChild(event, where) {
const { editors } = window.nextgenEditor;
const domShortcode = this.parentNode;
const editor = (editors.filter((instance) => instance.ui.view.element.contains(domShortcode)) || []).shift();
const name = domShortcode.getAttribute('name');
const shortcode = window.nextgenEditor.shortcodes[name];
if (editor) {
const viewShortcode = editor.editing.view.domConverter.mapDomToView(domShortcode);
const modelShortcode = editor.editing.mapper.toModelElement(viewShortcode);
editor.model.change((modelWriter) => {
let modelParentShortcode = modelShortcode.parent;
const insertPosition = modelWriter.createPositionAt(modelShortcode, where);
while (modelParentShortcode && modelParentShortcode.name !== 'shortcode-block') {
modelParentShortcode = modelParentShortcode.parent;
}
if (modelParentShortcode) {
editor.execute(`shortcode_${shortcode.name}`, { insertPosition, modelParentShortcode });
}
});
}
};
window.scBlockMoveChild = function scBlockMove(event, where) {
const { editors } = window.nextgenEditor;
const domShortcode = this.parentNode;
const editor = (editors.filter((instance) => instance.ui.view.element.contains(domShortcode)) || []).shift();
if (editor) {
const viewShortcode = editor.editing.view.domConverter.mapDomToView(domShortcode);
const modelShortcode = editor.editing.mapper.toModelElement(viewShortcode);
const domSiblingShortcode = where === 'up'
? domShortcode.previousSibling
: domShortcode.nextSibling;
const viewSiblingShortcode = editor.editing.view.domConverter.mapDomToView(domSiblingShortcode);
const modelSiblingShortcode = editor.editing.mapper.toModelElement(viewSiblingShortcode);
editor.model.change((modelWriter) => {
modelWriter.move(modelWriter.createRangeOn(modelShortcode), modelSiblingShortcode, where === 'up' ? 'before' : 'after');
});
}
};
@@ -0,0 +1,45 @@
window.nextgenEditor.addHook('hookInit', () => {
Object.values(window.nextgenEditor.shortcodes).forEach((shortcode) => {
shortcode.attributes = shortcode.attributes || {};
if (!shortcode.button) {
shortcode.button = { label: shortcode.title };
}
Object.values(shortcode.attributes).forEach((attribute) => {
if (attribute.default === undefined) {
attribute.default = '';
}
if (typeof attribute.default !== 'object') {
attribute.default = { value: attribute.default };
}
if (attribute.shorthand === undefined) {
attribute.shorthand = true;
}
});
if (shortcode.type === 'block' && !shortcode.titlebar) {
shortcode.titlebar = () => '';
}
if (!shortcode.content) {
shortcode.content = () => '';
}
if (shortcode.preserve) {
if (shortcode.preserve.block) {
window.nextgenEditor.addVariable('preserveBlockTags', shortcode.preserve.block);
}
if (shortcode.preserve.inline) {
window.nextgenEditor.addVariable('preserveInlineTags', shortcode.preserve.inline);
}
}
if (!shortcode.parent) {
window.nextgenEditor.addButton(`shortcode_${shortcode.name}`, {
command: `shortcode_${shortcode.name}`,
...shortcode.button,
});
}
});
});
@@ -0,0 +1,278 @@
shortcode-block {
background: #fff;
border: 1px solid #ccc;
display: block;
margin: 16px 0;
}
#admin-main .ck.ck-editor__editable_inline > :first-child {
margin-top: 16px;
}
#admin-main .ck.ck-editor__editable_inline > :last-child {
margin-bottom: 16px;
}
#admin-main .ck-editor shortcode-block.ck-shortcode-child:hover {
outline-color: #1f89e5;
}
#admin-main .ck-editor shortcode-block > .sc-header > .sc-title > p,
#admin-main .ck-editor shortcode-block > .sc-header > .sc-titlebar > p,
#admin-main .ck-editor shortcode-block > .sc-header > .sc-settings > p,
#admin-main .ck-editor shortcode-block > .sc-add > p,
#admin-main .ck-editor shortcode-block > .sc-move > p {
margin: 0;
}
shortcode-block > .sc-header {
align-items: center;
border-bottom: 1px solid #ccc;
display: flex;
font-size: 14px;
line-height: 1.5;
padding: 8px 8px;
}
shortcode-block > .sc-header > .sc-title > p > .sc-value {
font-weight: 700;
}
shortcode-block > .sc-header > .sc-titlebar {
margin-left: 24px;
}
shortcode-block > .sc-header > .sc-settings {
color: #ffc83d;
cursor: pointer;
font-size: 0;
line-height: 0;
margin-left: auto;
opacity: 0;
transition: opacity .2s ease, color .2s ease;
}
shortcode-block > .sc-header > .sc-settings:hover,
shortcode-block.ck-shortcode-child > .sc-header > .sc-settings,
shortcode-block.ck-widget_selected > .sc-header > .sc-settings {
color: #1f89e5;
}
shortcode-block.ck-widget_selected > .sc-header > .sc-settings:hover,
shortcode-block.ck-shortcode-child > .sc-header > .sc-settings:hover {
opacity: .5
}
shortcode-block:hover > .sc-header > .sc-settings,
shortcode-block.ck-widget_selected > .sc-header > .sc-settings {
opacity: 1;
}
shortcode-block > .sc-header > .sc-settings > p > svg {
height: 24px;
width: 24px;
}
shortcode-block-editable,
shortcode-block-readonly {
display: block;
padding: 0 8px;
}
shortcode-block-readonly > [data-cke-filler] {
display: none;
}
#admin-main .ck-editor shortcode-block-editable > :first-child {
margin-top: 14px;
}
#admin-main .ck-editor shortcode-block.ck-shortcode-child .ck-widget__type-around__button_after,
#admin-main .ck-editor shortcode-block.ck-shortcode-child .ck-widget__type-around__button_before {
display: none;
}
shortcode-block > .sc-add-child {
align-items: center;
display: none;
justify-content: center;
margin: 16px 0;
opacity: 0;
transition: opacity .2s ease;
}
shortcode-block > .sc-add-child.sc-visible {
display: flex;
}
shortcode-block:hover > .sc-add-child,
shortcode-block.ck-widget_selected > .sc-add-child {
opacity: 1;
z-index: 1;
}
shortcode-block > .sc-add-child > p {
align-items: center;
background: #ffc83d;
border-radius: 50%;
cursor: pointer;
display: flex;
height: 24px;
justify-content: center;
margin: 0!important;
transition: opacity .2s ease, background .2s ease;
width: 24px;
}
shortcode-block > .sc-add-child > p:hover,
shortcode-block.ck-widget_selected > .sc-add-child > p {
background: #1f89e5;
}
shortcode-block.ck-widget_selected > .sc-add-child > p:hover {
opacity: .5;
}
shortcode-block > .sc-add-child > p > svg {
color: #fff;
height: 20px;
transition: opacity .2s ease;
width: 20px;
}
shortcode-block > .sc-add {
left: 30px;
opacity: 0;
position: absolute;
transition: opacity .2s ease;
top: -12px;
}
shortcode-block > .sc-add-after {
bottom: -11px;
left: auto;
right: 30px;
top: auto;
}
shortcode-block:hover > .sc-add {
opacity: 1;
z-index: 1;
}
shortcode-block > .sc-add > p {
align-items: center;
background: #1f89e5;
border-radius: 50%;
cursor: pointer;
display: flex;
height: 20px;
justify-content: center;
width: 20px;
}
shortcode-block > .sc-add > p > svg {
color: #fff;
height: 16px;
transition: opacity .2s ease;
width: 16px;
}
shortcode-block > .sc-add:hover > p > svg {
opacity: .5;
}
shortcode-block > .sc-move {
background: #1f89e5;
border-radius: 50%;
cursor: pointer;
height: 20px;
opacity: 0;
position: absolute;
right: -12px;
transition: opacity .2s ease;
width: 20px;
top: 46px;
}
shortcode-block > .sc-move-up {
transform: rotate(180deg);
}
shortcode-block:first-child > .sc-move-up,
shortcode-block:last-child > .sc-move-down {
display: none;
}
shortcode-block > .sc-move-down {
bottom: 4px;
left: auto;
top: auto;
}
shortcode-block:hover > .sc-move {
opacity: 1;
z-index: 1;
}
shortcode-block > .sc-move > p > svg {
color: #fff;
height: 20px;
left: 1.5px;
position: absolute;
top: 2px;
transition: opacity .2s ease;
width: 20px;
}
shortcode-block > .sc-move:hover > p > svg {
opacity: .5;
}
shortcode-inline {
background: #fff;
border: 1px solid #ccc;
display: inline-flex;
margin-left: 2px;
margin-right: 1px;
vertical-align: middle;
}
shortcode-inline-editable,
shortcode-inline-readonly {
display: inline;
padding: 1px 4px 2px;
}
shortcode-inline > .sc-content {
display: inline-flex;
align-items: center;
}
shortcode-inline > .sc-settings {
align-items: center;
border-left: 1px solid #ccc;
cursor: pointer;
display: inline-flex;
font-size: 0;
line-height: 0;
padding: 0 2px;
transition: opacity .2s ease, color .2s ease;
}
shortcode-inline:hover > .sc-settings {
color: #ffc83d;
}
shortcode-inline > .sc-settings:hover,
shortcode-inline.ck-widget_selected > .sc-settings {
color: #1f89e5;
}
shortcode-inline.ck-widget_selected > .sc-settings:hover {
opacity: .5;
}
shortcode-inline > .sc-settings > svg {
height: 16px;
width: 16px;
}
@@ -0,0 +1,10 @@
import './command';
import './converters';
import './events';
import './init';
import './prerender';
import './postsave';
import './remove';
import './render';
import './save';
import './main.css';
@@ -0,0 +1,95 @@
window.nextgenEditor.addHook('hookHTMLtoMarkdown', {
weight: 50,
handler(options, editor, input) {
let output = input;
const realNames = Object.values(window.nextgenEditor.shortcodes).map((shortcode) => shortcode.realName)
.filter((value, index, self) => self.indexOf(value) === index);
const openingRegexp = realNames
.map((name) => `(\\[${name}[^\\]]*\\])`).join('|');
const hashMap = {};
let shortcodeCounter = 1;
while (shortcodeCounter > 0) {
shortcodeCounter = 0;
// eslint-disable-next-line no-loop-func
Object.values(window.nextgenEditor.shortcodes).forEach((shortcode) => {
const regexp = `(?<opening>\\[${shortcode.realName}[^\\]]*\\])(?<content>(((?!(${openingRegexp}|(\\[\\/${shortcode.realName}\\]))).)|\\n)*)(?<closing>\\[\\/${shortcode.realName}\\])`;
output = output.replace(new RegExp(regexp, 'g'), (...matches) => {
shortcodeCounter += 1;
const hash = Math.random().toString(36).slice(2);
hashMap[hash] = { shortcode, matches };
if (shortcode.child) {
const childName = shortcode.child.realName;
Object.keys(hashMap).forEach((childHash) => {
const childShortcode = hashMap[childHash].shortcode;
if (childShortcode === shortcode.child && childShortcode.name !== `${shortcode.realName}_${childName}` && matches[0].includes(childHash)) {
hashMap[childHash].shortcode = window.nextgenEditor.shortcodes[`${shortcode.realName}_${childName}`];
}
});
}
return hash;
});
});
}
shortcodeCounter = 1;
while (shortcodeCounter > 0) {
shortcodeCounter = 0;
// eslint-disable-next-line no-loop-func
Object.keys(hashMap).forEach((hash) => {
if (!output.includes(hash)) {
return;
}
shortcodeCounter += 1;
const { shortcode, matches } = hashMap[hash];
const groups = matches.pop();
if (shortcode.type === 'block') {
let content = groups.content.replace(/^\n/, '').replace(/\n$/, '');
if (shortcode.child) {
content = content.trim().split('\n').filter((line) => !!line).join('\n');
content = `\n${content}\n`;
}
if (shortcode.parent) {
content = `\n${content}\n`;
}
output = output.replace(hash, `${groups.opening}${content}${groups.closing}`);
}
if (shortcode.type === 'inline') {
output = output.replace(hash, matches[0]);
}
});
}
/*
Object.values(window.nextgenEditor.shortcodes).forEach((shortcode) => {
const regexp = `(?<opening>\\[${shortcode.realName}[^\\]]*\\])\n(?<content>(((?!(${openingRegexp}|(\\[\\/${shortcode.realName}\\]))).))*)\n(?<closing>\\[\\/${shortcode.realName}\\])`;
output = output.replace(new RegExp(regexp, 'g'), (...matches) => {
const groups = matches.pop();
return `${groups.opening}${groups.content}${groups.closing}`;
});
});
*/
return output;
},
});
@@ -0,0 +1,100 @@
window.nextgenEditor.addHook('hookMarkdowntoHTML', {
weight: -50,
handler(options, input) {
let output = input;
const realNames = Object.values(window.nextgenEditor.shortcodes).map((shortcode) => shortcode.realName)
.filter((value, index, self) => self.indexOf(value) === index);
const openingRegexp = realNames
.map((name) => `(\\[${name}[^\\]]*\\])`).join('|');
realNames.forEach((name) => {
const regexp = `\\[${name}(?<attributes>(=| +).+?(?=/]))?\\/\\]`;
output = output.replace(new RegExp(regexp, 'g'), (...matches) => {
const groups = matches.pop();
const attributes = groups.attributes.trim()
? `${groups.attributes}`
: '';
return `[${name}${attributes}][/${name}]`;
});
});
const hashMap = {};
let shortcodeCounter = 1;
while (shortcodeCounter > 0) {
shortcodeCounter = 0;
// eslint-disable-next-line no-loop-func
Object.values(window.nextgenEditor.shortcodes).forEach((shortcode) => {
const regexp = `(?<spaces_before> *)\\[${shortcode.realName}(?<attributes>(=| +)[^\\]]*)?\\](?<content>(((?!(${openingRegexp}|(\\[\\/${shortcode.realName}\\]))).)|\\n)*)\\[\\/${shortcode.realName}\\](?<spaces_after> *)`;
output = output.replace(new RegExp(regexp, 'g'), (...matches) => {
shortcodeCounter += 1;
const hash = Math.random().toString(36).slice(2);
hashMap[hash] = { shortcode, matches };
if (shortcode.child) {
const childName = shortcode.child.realName;
Object.keys(hashMap).forEach((childHash) => {
const childShortcode = hashMap[childHash].shortcode;
if (childShortcode === shortcode.child && childShortcode.name !== `${shortcode.realName}_${childName}` && matches[0].includes(childHash)) {
hashMap[childHash].shortcode = window.nextgenEditor.shortcodes[`${shortcode.realName}_${childName}`];
}
});
}
return hash;
});
});
}
shortcodeCounter = 1;
while (shortcodeCounter > 0) {
shortcodeCounter = 0;
// eslint-disable-next-line no-loop-func
Object.keys(hashMap).forEach((hash) => {
if (!output.includes(hash)) {
return;
}
shortcodeCounter += 1;
const { shortcode, matches } = hashMap[hash];
const groups = matches.pop();
const spacesBefore = groups.spaces_before.replace(/ /g, '&nbsp;');
const spacesAfter = groups.spaces_after.replace(/ /g, '&nbsp;');
if (shortcode.type === 'block') {
let content = groups.content.trim();
if (groups.spaces_before.length) {
content = content.replace(new RegExp(`^( ){${groups.spaces_before.length}}`, 'gm'), '');
}
const replacement = `\n\n[${shortcode.name}${groups.attributes || ''}]\n\n${content}\n\n[/${shortcode.name}]\n\n`;
output = output.replace(new RegExp(`(\\n)?(\\n)?${hash}(\\n)?(\\n)?`), replacement);
}
if (shortcode.type === 'inline') {
output = output.replace(hash, `${spacesBefore}[${shortcode.name}${groups.attributes || ''}]${groups.content}[/${shortcode.name}]${spacesAfter}`);
}
});
}
output = output.replace(/^\n\n/, '').replace(/\n\n$/, '');
return output;
},
});
@@ -0,0 +1,55 @@
window.nextgenEditor.addPlugin('GravShortcodeCoreRemove', {
init() {
const deleteBackwardCommand = this.editor.commands.get('delete');
const deleteForwardCommand = this.editor.commands.get('forwardDelete');
const preDelete = (event) => {
const selectedElement = this.editor.model.document.selection.getSelectedElement();
if (selectedElement && selectedElement.name === 'shortcode-block') {
const name = selectedElement.getAttribute('name');
const shortcode = window.nextgenEditor.shortcodes[name];
if (shortcode.parent) {
const viewShortcode = this.editor.editing.mapper.toViewElement(selectedElement);
const domShortcode = this.editor.editing.view.domConverter.mapViewToDom(viewShortcode);
const domParentShortcode = domShortcode.closest(`shortcode-block[name="${shortcode.parent.name}"]`);
event.childShortcodeDeleted = true;
event.modelShortcodeBlockReadOnly = selectedElement.parent;
event.domParentShortcode = domParentShortcode;
}
}
};
const postDelete = (event) => {
if (event.childShortcodeDeleted) {
const { domParentShortcode, modelShortcodeBlockReadOnly } = event;
const children = [...modelShortcodeBlockReadOnly.getChildren()];
const scChildren = children.filter((child) => child.name === 'shortcode-block');
const otherChildren = children.filter((child) => child.name !== 'shortcode-block');
setTimeout(() => {
this.editor.model.change((modelWriter) => {
otherChildren.forEach((modelChild) => {
if (modelChild.name === 'paragraph' && modelChild.childCount === 0) {
modelWriter.remove(modelChild);
}
});
});
});
if (!scChildren.length) {
domParentShortcode.querySelector('shortcode-block > .sc-add-child').classList.add('sc-visible');
}
}
};
deleteBackwardCommand.on('execute', preDelete, { priority: 'highest' });
deleteForwardCommand.on('execute', preDelete, { priority: 'highest' });
deleteBackwardCommand.on('execute', postDelete, { priority: 'lowest' });
deleteForwardCommand.on('execute', postDelete, { priority: 'lowest' });
},
});
@@ -0,0 +1,95 @@
import uncollapse from './uncollapse';
window.nextgenEditor.addHook('hookMarkdowntoHTML', {
weight: 50,
handler(options, input) {
let output = input;
let shortcodeCounter = 1;
const openingRegexp = Object.keys(window.nextgenEditor.shortcodes).map((name) => `(\\[${name}[^\\]]*\\])`).join('|');
while (shortcodeCounter > 0) {
shortcodeCounter = 0;
// eslint-disable-next-line no-loop-func
Object.values(window.nextgenEditor.shortcodes).forEach((shortcode) => {
const regexp = `(?<p1><p>)?\\[${shortcode.name}(?<attributes>(=| +)[^\\]]*)?\\](<\\/p>)?(?<content>(((?!(${openingRegexp}|(\\[\\/${shortcode.name}\\]))).)|\\n)*)\\[\\/${shortcode.name}\\](?<p2><\\/p>)?`;
output = output.replace(new RegExp(regexp, 'g'), (...matches) => {
shortcodeCounter += 1;
const groups = matches.pop();
let content = shortcode.type === 'block'
? groups.content.replace(/<p>$/, '')
: groups.content;
const bbcode = Object.keys(shortcode.attributes).reduce((acc, attrName) => acc || (shortcode.attributes[attrName].bbcode && shortcode.attributes[attrName].shorthand && attrName), '');
const innerHTMLAttribute = Object.keys(shortcode.attributes).reduce((acc, attrName) => acc || (shortcode.attributes[attrName].innerHTML && attrName), '');
let attrGroup = bbcode && groups.attributes && groups.attributes.startsWith('=')
? `${bbcode}${groups.attributes}`
: groups.attributes || '';
if (innerHTMLAttribute) {
const innerHTML = shortcode.type === 'block'
? content.replace(/^<p>/, '').replace(/<\/p>$/, '').replace(/^&nbsp;$/, '')
: content.replace(/^&nbsp;$/, '');
attrGroup = attrGroup
? `${attrGroup} ${innerHTMLAttribute}="${innerHTML}"`
: `${innerHTMLAttribute}="${innerHTML}"`;
content = '';
}
const domAttributes = new DOMParser().parseFromString(`<div ${attrGroup}></div>`, 'text/html').body.firstChild.attributes;
const attributes = Object.keys(shortcode.attributes).reduce((acc, attrName) => {
const attribute = shortcode.attributes[attrName];
let attrValue = domAttributes.getNamedItem(attrName)
? domAttributes.getNamedItem(attrName).value
: attribute.default.value;
if (attribute.type === Boolean && domAttributes.getNamedItem(attrName)) {
attrValue = domAttributes.getNamedItem(attrName) !== 'false';
}
if (attribute.type === Number) {
attrValue = +attrValue;
}
acc[attrName] = attrValue;
return acc;
}, {});
let replacement = '';
const attributesEncoded = encodeURIComponent(JSON.stringify(attributes));
if (shortcode.type === 'block') {
replacement += `<shortcode-block name="${shortcode.name}" attributes="${attributesEncoded}">`;
replacement += content;
replacement += '</shortcode-block>';
}
if (shortcode.type === 'inline') {
replacement += groups.p1 || '';
replacement += `<shortcode-inline name="${shortcode.name}" attributes="${attributesEncoded}">`;
replacement += content;
replacement += '</shortcode-inline>';
replacement += groups.p2 || '';
}
return replacement;
});
});
}
output = uncollapse(output);
return output;
},
});
@@ -0,0 +1,80 @@
import collapse from './collapse';
window.nextgenEditor.addHook('hookHTMLtoMarkdown', {
weight: -50,
handler(options, editor, input) {
let output = input;
output = collapse(output);
const domOutput = new DOMParser().parseFromString(output, 'text/html');
let domShortcode = domOutput.querySelector('shortcode-block, shortcode-inline');
while (domShortcode) {
const name = domShortcode.getAttribute('name');
const shortcode = window.nextgenEditor.shortcodes[name];
const attributes = JSON.parse(decodeURIComponent(domShortcode.getAttribute('attributes')));
const innerHTMLAttribute = Object.keys(shortcode.attributes).reduce((acc, attrName) => acc || (shortcode.attributes[attrName].innerHTML && attrName), '');
const attrLine = Object.keys(shortcode.attributes).reduce((acc, attrName) => {
const attribute = shortcode.attributes[attrName];
if (attribute.type === Boolean) {
return attributes[attrName]
? `${acc} ${attrName}`
: acc;
}
if (attributes[attrName] === attribute.default.value && !attribute.default.preserve) {
return acc;
}
if (attribute.bbcode && attribute.shorthand) {
return `="${attributes[attrName]}"${acc}`;
}
if (attribute.innerHTML) {
return acc;
}
return `${acc} ${attrName}="${attributes[attrName]}"`;
}, '');
if (shortcode.type === 'block') {
if (domShortcode.innerHTML === '<p>&nbsp;</p>') {
domShortcode.innerHTML = '';
}
if (innerHTMLAttribute) {
domShortcode.outerHTML = `<p>[${shortcode.realName}${attrLine}]${attributes[innerHTMLAttribute]}[/${shortcode.realName}]</p>`;
} else if (domShortcode.innerHTML) {
domShortcode.outerHTML = `<p>[${shortcode.realName}${attrLine}]</p>${domShortcode.innerHTML}<p>[/${shortcode.realName}]</p>`;
} else {
domShortcode.outerHTML = `<p>[${shortcode.realName}${attrLine} /]</p>`;
}
}
if (shortcode.type === 'inline') {
if (domShortcode.innerHTML === '&nbsp;') {
domShortcode.innerHTML = '';
}
if (innerHTMLAttribute) {
domShortcode.outerHTML = `[${shortcode.realName}${attrLine}]${attributes[innerHTMLAttribute]}[/${shortcode.realName}]`;
} else if (domShortcode.innerHTML) {
domShortcode.outerHTML = `[${shortcode.realName}${attrLine}]${domShortcode.innerHTML}[/${shortcode.realName}]`;
} else {
domShortcode.outerHTML = `[${shortcode.realName}${attrLine} /]`;
}
}
domShortcode = domOutput.querySelector('shortcode-block, shortcode-inline');
}
output = domOutput.body.innerHTML;
return output;
},
});
@@ -0,0 +1,153 @@
import collapse from './collapse';
import uncollapse from './uncollapse';
const { showSettingsPopup } = window.nextgenEditor.exports;
export default function displaySettings(domShortcode) {
const { editors } = window.nextgenEditor;
const editor = (editors.filter((instance) => instance.ui.view.element.contains(domShortcode)) || []).shift();
const name = domShortcode.getAttribute('name');
const shortcode = window.nextgenEditor.shortcodes[name];
const plugin = window.nextgenEditor.shortcodePlugins[shortcode.plugin];
if (editor) {
const viewShortcode = editor.editing.view.domConverter.mapDomToView(domShortcode);
let modelShortcode = editor.editing.mapper.toModelElement(viewShortcode);
const currentAttributes = JSON.parse(decodeURIComponent(domShortcode.getAttribute('attributes')));
const domDisplayPoint = shortcode.type === 'block'
? domShortcode.querySelector('.sc-header > .sc-settings')
: domShortcode;
const title = []
.concat([
(plugin && plugin.title) || '',
(shortcode.parent && shortcode.parent.title) || '',
shortcode.title || '',
])
.filter((item) => !!item)
.join(' / ');
const argsForPopup = {
title,
domDisplayPoint,
debounceDelay: 1000,
attributes: shortcode.attributes,
currentAttributes,
parentAttributes: null,
childAttributes: null,
};
if (shortcode.parent) {
const domParentShortcode = domShortcode.closest(`shortcode-block[name="${shortcode.parent.name}"]`);
argsForPopup.parentAttributes = domParentShortcode
? JSON.parse(decodeURIComponent(domParentShortcode.getAttribute('attributes')))
: {};
}
if (shortcode.child) {
argsForPopup.childAttributes = [];
const childNodes = [...domShortcode.querySelectorAll(`shortcode-block shortcode-block[name="${shortcode.child.name}"]`)];
const deepChildNodes = [...domShortcode.querySelectorAll(`shortcode-block shortcode-block shortcode-block[name="${shortcode.child.name}"]`)];
childNodes
.filter((domChildShortcode) => !deepChildNodes.includes(domChildShortcode))
.forEach((domChildShortcode) => {
const childAttributes = JSON.parse(decodeURIComponent(domChildShortcode.getAttribute('attributes')));
argsForPopup.childAttributes.push(childAttributes);
});
}
argsForPopup.deleteItem = () => editor.execute('delete');
argsForPopup.changeAttributes = () => {
editor.model.change((modelWriter) => {
modelWriter.setAttribute('attributes', encodeURIComponent(JSON.stringify(currentAttributes)), modelShortcode);
const convertContext = shortcode.type === 'inline'
? '$block'
: '$root';
if (shortcode.parent) {
const viewOldShortcode = editor.editing.mapper.toViewElement(modelShortcode);
const domOldShortcode = editor.editing.view.domConverter.mapViewToDom(viewOldShortcode);
if (!domOldShortcode) {
return;
}
const domOldParentShortcode = domOldShortcode.parentNode.closest('shortcode-block');
const viewOldParentShortcode = editor.editing.view.domConverter.mapDomToView(domOldParentShortcode);
const modelOldParentShortcode = editor.editing.mapper.toModelElement(viewOldParentShortcode);
const childNodes = [...domOldParentShortcode.querySelectorAll('shortcode-block shortcode-block')];
const deepChildNodes = [...domOldParentShortcode.querySelectorAll('shortcode-block shortcode-block shortcode-block')];
const childIndex = childNodes
.filter((domChildShortcode) => !deepChildNodes.includes(domChildShortcode))
.indexOf(domOldShortcode);
const insertPosition = modelWriter.createPositionBefore(modelOldParentShortcode);
const modelOldParentClonedShortcode = modelWriter.cloneElement(modelOldParentShortcode);
const modelOldParentFragment = modelWriter.createDocumentFragment();
modelWriter.append(modelOldParentClonedShortcode, modelOldParentFragment);
const viewOldParentClonedShortcode = editor.data.toView(modelOldParentFragment).getChild(0);
const dataOldParentClonedShortcode = editor.data.processor.toData(viewOldParentClonedShortcode);
const dataNewParentShortcode = uncollapse(collapse(dataOldParentClonedShortcode));
const viewNewParentShortcode = editor.data.processor.toView(dataNewParentShortcode).getChild(0);
const modelNewParentShortcode = editor.data.toModel(viewNewParentShortcode, convertContext).getChild(0);
modelWriter.remove(modelOldParentShortcode);
modelWriter.insert(modelNewParentShortcode, insertPosition);
setTimeout(() => {
const viewParentShortcode = editor.editing.mapper.toViewElement(modelNewParentShortcode);
const domParentShortcode = editor.editing.view.domConverter.mapViewToDom(viewParentShortcode);
const childNewNodes = [...domParentShortcode.querySelectorAll('shortcode-block shortcode-block')];
const deepNewChildNodes = [...domParentShortcode.querySelectorAll('shortcode-block shortcode-block shortcode-block')];
const domNewShortcode = childNewNodes.filter((domChildShortcode) => !deepNewChildNodes.includes(domChildShortcode))[childIndex];
const viewNewShortcode = editor.editing.view.domConverter.mapDomToView(domNewShortcode);
const modelNewShortcode = editor.editing.mapper.toModelElement(viewNewShortcode);
editor.model.change((modelWriter2) => {
modelWriter2.setSelection(modelNewShortcode, 'on');
modelShortcode = modelNewShortcode;
});
});
return;
}
const insertPosition = modelWriter.createPositionBefore(modelShortcode);
const modelOldShortcode = modelWriter.cloneElement(modelShortcode);
const modelOldFragment = modelWriter.createDocumentFragment();
modelWriter.append(modelOldShortcode, modelOldFragment);
const viewOldShortcode = editor.data.toView(modelOldFragment).getChild(0);
const dataOldShortcode = editor.data.processor.toData(viewOldShortcode);
const dataNewShortcode = uncollapse(collapse(dataOldShortcode));
const viewNewShortcode = editor.data.processor.toView(dataNewShortcode).getChild(0);
const modelNewShortcode = editor.data.toModel(viewNewShortcode, convertContext).getChild(0);
modelWriter.remove(modelShortcode);
modelWriter.insert(modelNewShortcode, insertPosition);
modelWriter.setSelection(modelNewShortcode, 'on');
modelShortcode = modelNewShortcode;
});
};
showSettingsPopup(argsForPopup);
}
}
@@ -0,0 +1,164 @@
export default function uncollapse(input, args) {
const domOutput = new DOMParser().parseFromString(input, 'text/html');
[...domOutput.querySelectorAll('shortcode-block, shortcode-inline')].forEach((domShortcode) => {
domShortcode.setAttribute('sc-rendered', false);
});
let domShortcode = domOutput.querySelector('shortcode-block[sc-rendered], shortcode-inline[sc-rendered]');
while (domShortcode) {
const name = domShortcode.getAttribute('name');
const shortcode = window.nextgenEditor.shortcodes[name];
const attributes = JSON.parse(decodeURIComponent(domShortcode.getAttribute('attributes')));
domShortcode.classList.add('ck-shortcode');
domShortcode.classList.add(`ck-shortcode-${shortcode.type}`);
domShortcode.removeAttribute('sc-rendered');
const argsForRender = {
shortcode,
attributes,
innerHTML: domShortcode.innerHTML,
parentAttributes: null,
childAttributes: null,
};
let innerHTML = '';
if (shortcode.type === 'block') {
if (shortcode.parent) {
domShortcode.classList.add('ck-shortcode-child');
const domParentShortcode = domShortcode.closest(`shortcode-block[name="${shortcode.parent.name}"]`);
argsForRender.parentAttributes = !args || !args.parentAttributes
? domParentShortcode
? JSON.parse(decodeURIComponent(domParentShortcode.getAttribute('attributes')))
: {}
: args.parentAttributes;
}
if (shortcode.child) {
argsForRender.childAttributes = [];
domShortcode.classList.add('ck-shortcode-parent');
const childNodes = [...domShortcode.querySelectorAll(`shortcode-block shortcode-block[name="${shortcode.child.name}"]`)];
const deepChildNodes = [...domShortcode.querySelectorAll(`shortcode-block shortcode-block shortcode-block[name="${shortcode.child.name}"]`)];
childNodes
.filter((domChildShortcode) => !deepChildNodes.includes(domChildShortcode))
.forEach((domChildShortcode) => {
const childAttributes = JSON.parse(decodeURIComponent(domChildShortcode.getAttribute('attributes')));
argsForRender.childAttributes.push(childAttributes);
});
}
/* eslint-disable indent, no-multi-spaces */
innerHTML += '<div class="sc-header">';
innerHTML += `<div class="sc-title">Shortcode - <span class="sc-value">${shortcode.title}</span></div>`;
innerHTML += `<div class="sc-titlebar">${shortcode.titlebar(argsForRender)}</div>`;
innerHTML += '<div class="sc-settings">';
innerHTML += '<svg viewBox="0 0 24 24" fill="currentColor" stroke="none">';
innerHTML += '<path d="M9 4.58V4c0-1.1.9-2 2-2h2a2 2 0 0 1 2 2v.58a8 8 0 0 1 1.92 1.11l.5-.29a2 2 0 0 1 2.74.73l1 1.74a2 2 0 0 1-.73 2.73l-.5.29a8.06 8.06 0 0 1 0 2.22l.5.3a2 2 0 0 1 .73 2.72l-1 1.74a2 2 0 0 1-2.73.73l-.5-.3A8 8 0 0 1 15 19.43V20a2 2 0 0 1-2 2h-2a2 2 0 0 1-2-2v-.58a8 8 0 0 1-1.92-1.11l-.5.29a2 2 0 0 1-2.74-.73l-1-1.74a2 2 0 0 1 .73-2.73l.5-.29a8.06 8.06 0 0 1 0-2.22l-.5-.3a2 2 0 0 1-.73-2.72l1-1.74a2 2 0 0 1 2.73-.73l.5.3A8 8 0 0 1 9 4.57zM7.88 7.64l-.54.51-1.77-1.02-1 1.74 1.76 1.01-.17.73a6.02 6.02 0 0 0 0 2.78l.17.73-1.76 1.01 1 1.74 1.77-1.02.54.51a6 6 0 0 0 2.4 1.4l.72.2V20h2v-2.04l.71-.2a6 6 0 0 0 2.41-1.4l.54-.51 1.77 1.02 1-1.74-1.76-1.01.17-.73a6.02 6.02 0 0 0 0-2.78l-.17-.73 1.76-1.01-1-1.74-1.77 1.02-.54-.51a6 6 0 0 0-2.4-1.4l-.72-.2V4h-2v2.04l-.71.2a6 6 0 0 0-2.41 1.4zM12 16a4 4 0 1 1 0-8 4 4 0 0 1 0 8zm0-2a2 2 0 1 0 0-4 2 2 0 0 0 0 4z"></path>';
innerHTML += '</svg>';
innerHTML += '</div>';
innerHTML += '</div>';
innerHTML += '<div class="sc-content">';
innerHTML += shortcode.content(argsForRender)
.replace('{{content_editable}}', `<shortcode-block-editable>${domShortcode.innerHTML}</shortcode-block-editable>`)
.replace('{{content_readonly}}', `<shortcode-block-readonly>${domShortcode.innerHTML}</shortcode-block-readonly>`);
innerHTML += '</div>';
if (shortcode.child) {
const visible = !domShortcode.innerHTML ? ' sc-visible' : '';
innerHTML += `<div class="sc-add-child${visible}" title="Insert new ${shortcode.child.title}">`;
innerHTML += '<svg viewBox="0 0 24 24" fill="currentColor" stroke="none">';
innerHTML += '<path d="M17 11a1 1 0 0 1 0 2h-4v4a1 1 0 0 1-2 0v-4H7a1 1 0 0 1 0-2h4V7a1 1 0 0 1 2 0v4h4z"></path>';
innerHTML += '</svg>';
innerHTML += '</div>';
}
if (shortcode.parent) {
['before', 'after'].forEach((where) => {
innerHTML += `<div class="sc-add sc-add-${where}" title="Insert new ${shortcode.title} ${where}">`;
innerHTML += '<svg viewBox="0 0 24 24" fill="currentColor" stroke="none">';
innerHTML += '<path d="M17 11a1 1 0 0 1 0 2h-4v4a1 1 0 0 1-2 0v-4H7a1 1 0 0 1 0-2h4V7a1 1 0 0 1 2 0v4h4z"></path>';
innerHTML += '</svg>';
innerHTML += '</div>';
});
['up', 'down'].forEach((where) => {
innerHTML += `<div class="sc-move sc-move-${where}" title="Move ${shortcode.title} ${where}">`;
innerHTML += '<svg viewBox="0 0 24 24" fill="currentColor" stroke="none">';
innerHTML += '<path fill-rule="evenodd" clip-rule="evenodd" d="M5.293 7.293a1 1 0 011.414 0L10 10.586l3.293-3.293a1 1 0 111.414 1.414l-4 4a1 1 0 01-1.414 0l-4-4a1 1 0 010-1.414z"></path>';
innerHTML += '</svg>';
innerHTML += '</div>';
});
}
/* eslint-enable indent, no-multi-spaces */
}
if (shortcode.type === 'inline') {
/* eslint-disable indent, no-multi-spaces */
innerHTML += '<span class="sc-content">';
innerHTML += shortcode.content(argsForRender)
.replace('{{content_editable}}', `<shortcode-inline-editable>${domShortcode.innerHTML}</shortcode-inline-editable>`)
.replace('{{content_readonly}}', `<shortcode-inline-readonly>${domShortcode.innerHTML}</shortcode-inline-readonly>`);
innerHTML += '</span>';
innerHTML += '<span class="sc-settings">';
innerHTML += '<svg viewBox="0 0 24 24" fill="currentColor" stroke="none">';
innerHTML += '<path d="M9 4.58V4c0-1.1.9-2 2-2h2a2 2 0 0 1 2 2v.58a8 8 0 0 1 1.92 1.11l.5-.29a2 2 0 0 1 2.74.73l1 1.74a2 2 0 0 1-.73 2.73l-.5.29a8.06 8.06 0 0 1 0 2.22l.5.3a2 2 0 0 1 .73 2.72l-1 1.74a2 2 0 0 1-2.73.73l-.5-.3A8 8 0 0 1 15 19.43V20a2 2 0 0 1-2 2h-2a2 2 0 0 1-2-2v-.58a8 8 0 0 1-1.92-1.11l-.5.29a2 2 0 0 1-2.74-.73l-1-1.74a2 2 0 0 1 .73-2.73l.5-.29a8.06 8.06 0 0 1 0-2.22l-.5-.3a2 2 0 0 1-.73-2.72l1-1.74a2 2 0 0 1 2.73-.73l.5.3A8 8 0 0 1 9 4.57zM7.88 7.64l-.54.51-1.77-1.02-1 1.74 1.76 1.01-.17.73a6.02 6.02 0 0 0 0 2.78l.17.73-1.76 1.01 1 1.74 1.77-1.02.54.51a6 6 0 0 0 2.4 1.4l.72.2V20h2v-2.04l.71-.2a6 6 0 0 0 2.41-1.4l.54-.51 1.77 1.02 1-1.74-1.76-1.01.17-.73a6.02 6.02 0 0 0 0-2.78l-.17-.73 1.76-1.01-1-1.74-1.77 1.02-.54-.51a6 6 0 0 0-2.4-1.4l-.72-.2V4h-2v2.04l-.71.2a6 6 0 0 0-2.41 1.4zM12 16a4 4 0 1 1 0-8 4 4 0 0 1 0 8zm0-2a2 2 0 1 0 0-4 2 2 0 0 0 0 4z"></path>';
innerHTML += '</svg>';
innerHTML += '</span>';
/* eslint-enable indent, no-multi-spaces */
}
domShortcode.innerHTML = innerHTML;
domShortcode = domOutput.querySelector('shortcode-block[sc-rendered], shortcode-inline[sc-rendered]');
}
return domOutput.body.innerHTML;
}
document.addEventListener('click', (event) => {
const { target } = event;
const list = ['sc-settings', 'sc-move', 'sc-add', 'sc-add-child'];
const action = { element: null, className: null };
const isAction = list.some((item) => {
let match = target.classList.contains(item);
if (match) {
action.element = target;
action.className = item;
return true;
}
match = target.closest(`.${item}`);
if (match) {
action.element = match;
action.className = item;
return true;
}
return false;
});
if (isAction) {
switch (action.className) {
case 'sc-move':
window.scBlockMoveChild.call(action.element, event, action.element.classList.contains('sc-move-up') ? 'up' : 'down');
break;
case 'sc-add':
window.scBlockAddChild.call(action.element, event, action.element.classList.contains('sc-add-before') ? 'before' : 'after');
break;
case 'sc-add-child':
window.scBlockAddChildFromParent.call(action.element, event);
break;
case 'sc-settings':
default:
window.scDisplaySettings.call(action.element, event);
}
}
});
@@ -0,0 +1,31 @@
const DirectoryNamedWebpackPlugin = require('directory-named-webpack-plugin');
module.exports = {
filenameHashing: false,
publicPath: process.env.NODE_ENV === 'development'
? `http://${process.env.DEV_HOST}:${process.env.DEV_PORT}/`
: '/',
configureWebpack: {
resolve: {
plugins: [
new DirectoryNamedWebpackPlugin(),
],
},
optimization: {
splitChunks: false,
},
},
chainWebpack: (webpackConfig) => {
webpackConfig.plugins.delete('html');
webpackConfig.plugins.delete('preload');
webpackConfig.plugins.delete('prefetch');
},
devServer: {
host: process.env.DEV_HOST,
port: process.env.DEV_PORT,
disableHostCheck: true,
headers: {
'Access-Control-Allow-Origin': '*',
},
},
};
File diff suppressed because it is too large Load Diff