@ebl-vue/editor-full 1.0.8
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.postcssrc.yml +33 -0
- package/LICENSE +21 -0
- package/README.md +1 -0
- package/dist/index.d.ts +5 -0
- package/dist/index.mjs +2565 -0
- package/dist/index.mjs.map +1 -0
- package/package.json +55 -0
- package/postcss.config.js +15 -0
- package/src/components/Editor/Editor.vue +209 -0
- package/src/components/index.ts +27 -0
- package/src/constants/index.ts +1 -0
- package/src/i18n/zh-cn.ts +151 -0
- package/src/icons/index.ts +78 -0
- package/src/index.ts +11 -0
- package/src/installer.ts +22 -0
- package/src/plugins/alert/index.css +150 -0
- package/src/plugins/alert/index.ts +463 -0
- package/src/plugins/block-alignment/index.css +9 -0
- package/src/plugins/block-alignment/index.ts +116 -0
- package/src/plugins/block-alignment/readme.md +1 -0
- package/src/plugins/code/LICENSE +21 -0
- package/src/plugins/code/index.css +120 -0
- package/src/plugins/code/index.ts +530 -0
- package/src/plugins/code/utils/string.ts +34 -0
- package/src/plugins/color-picker/index.ts +138 -0
- package/src/plugins/color-picker/styles.css +27 -0
- package/src/plugins/delimiter/index.css +14 -0
- package/src/plugins/delimiter/index.ts +122 -0
- package/src/plugins/drag-drop/index.css +19 -0
- package/src/plugins/drag-drop/index.ts +151 -0
- package/src/plugins/drag-drop/readme.md +1 -0
- package/src/plugins/header/H1.ts +405 -0
- package/src/plugins/header/H2.ts +403 -0
- package/src/plugins/header/H3.ts +404 -0
- package/src/plugins/header/H4.ts +405 -0
- package/src/plugins/header/H5.ts +405 -0
- package/src/plugins/header/H6.ts +406 -0
- package/src/plugins/header/index.css +20 -0
- package/src/plugins/header/index.ts +15 -0
- package/src/plugins/header/types.d.ts +46 -0
- package/src/plugins/indent/index.css +86 -0
- package/src/plugins/indent/index.ts +697 -0
- package/src/plugins/inline-code/index.css +11 -0
- package/src/plugins/inline-code/index.ts +205 -0
- package/src/plugins/list/ListRenderer/ChecklistRenderer.ts +211 -0
- package/src/plugins/list/ListRenderer/ListRenderer.ts +73 -0
- package/src/plugins/list/ListRenderer/OrderedListRenderer.ts +123 -0
- package/src/plugins/list/ListRenderer/UnorderedListRenderer.ts +123 -0
- package/src/plugins/list/ListRenderer/index.ts +6 -0
- package/src/plugins/list/ListTabulator/index.ts +1179 -0
- package/src/plugins/list/index.ts +502 -0
- package/src/plugins/list/styles/CssPrefix.ts +4 -0
- package/src/plugins/list/styles/icons/index.ts +10 -0
- package/src/plugins/list/styles/input.css +36 -0
- package/src/plugins/list/styles/list.css +165 -0
- package/src/plugins/list/types/Elements.ts +14 -0
- package/src/plugins/list/types/ItemMeta.ts +40 -0
- package/src/plugins/list/types/ListParams.ts +102 -0
- package/src/plugins/list/types/ListRenderer.ts +6 -0
- package/src/plugins/list/types/OlCounterType.ts +63 -0
- package/src/plugins/list/types/index.ts +14 -0
- package/src/plugins/list/utils/focusItem.ts +18 -0
- package/src/plugins/list/utils/getChildItems.ts +40 -0
- package/src/plugins/list/utils/getItemChildWrapper.ts +10 -0
- package/src/plugins/list/utils/getItemContentElement.ts +10 -0
- package/src/plugins/list/utils/getSiblings.ts +52 -0
- package/src/plugins/list/utils/isLastItem.ts +9 -0
- package/src/plugins/list/utils/itemHasSublist.ts +10 -0
- package/src/plugins/list/utils/normalizeData.ts +84 -0
- package/src/plugins/list/utils/removeChildWrapperIfEmpty.ts +31 -0
- package/src/plugins/list/utils/renderToolboxInput.ts +105 -0
- package/src/plugins/list/utils/stripNumbers.ts +7 -0
- package/src/plugins/list/utils/type-guards.ts +8 -0
- package/src/plugins/list.md +15 -0
- package/src/plugins/marker/index.css +4 -0
- package/src/plugins/marker/index.ts +187 -0
- package/src/plugins/paragraph/index.css +23 -0
- package/src/plugins/paragraph/index.ts +380 -0
- package/src/plugins/paragraph/types/icons.d.ts +4 -0
- package/src/plugins/paragraph/utils/makeFragment.ts +17 -0
- package/src/plugins/quote/index.css +26 -0
- package/src/plugins/quote/index.ts +206 -0
- package/src/plugins/table/index.ts +4 -0
- package/src/plugins/table/plugin.ts +254 -0
- package/src/plugins/table/style.css +388 -0
- package/src/plugins/table/table.ts +1192 -0
- package/src/plugins/table/toolbox.ts +165 -0
- package/src/plugins/table/utils/dom.ts +128 -0
- package/src/plugins/table/utils/popover.ts +172 -0
- package/src/plugins/table/utils/throttled.ts +22 -0
- package/src/plugins/underline/index.css +3 -0
- package/src/plugins/underline/index.ts +216 -0
- package/src/plugins/undo/index.ts +509 -0
- package/src/plugins/undo/observer.ts +101 -0
- package/src/style.css +89 -0
- package/src/utils/index.ts +15 -0
- package/src/utils/install.ts +19 -0
- package/tsconfig.json +37 -0
- package/types/index.d.ts +13 -0
- package/types/plugins/index.d.ts +0 -0
- package/vite.config.ts +79 -0
package/src/index.ts
ADDED
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
|
|
2
|
+
|
|
3
|
+
import './style.css'
|
|
4
|
+
import { createInstaller } from './installer'
|
|
5
|
+
import Components from './components';
|
|
6
|
+
|
|
7
|
+
const installer = createInstaller(Components)
|
|
8
|
+
export const install = installer.install
|
|
9
|
+
export const version = installer.version
|
|
10
|
+
export default installer;
|
|
11
|
+
export * from "./components";
|
package/src/installer.ts
ADDED
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
import type { App, Plugin } from 'vue'
|
|
2
|
+
import { version } from '../package.json'
|
|
3
|
+
|
|
4
|
+
import { INSTALLED_KEY } from "./constants";
|
|
5
|
+
|
|
6
|
+
export const createInstaller = (components: Plugin[] = []) => {
|
|
7
|
+
const install = (app: App,iconfig?: any) => {
|
|
8
|
+
if (app[INSTALLED_KEY]) return
|
|
9
|
+
|
|
10
|
+
app[INSTALLED_KEY] = true
|
|
11
|
+
components.forEach((c) => app.use(c))
|
|
12
|
+
if(iconfig) {
|
|
13
|
+
app.provide("locale",iconfig.locale);
|
|
14
|
+
}
|
|
15
|
+
|
|
16
|
+
}
|
|
17
|
+
|
|
18
|
+
return {
|
|
19
|
+
version,
|
|
20
|
+
install,
|
|
21
|
+
}
|
|
22
|
+
}
|
|
@@ -0,0 +1,150 @@
|
|
|
1
|
+
.cdx-alert {
|
|
2
|
+
position: relative;
|
|
3
|
+
padding: 10px;
|
|
4
|
+
border-radius: 5px;
|
|
5
|
+
margin-bottom: 10px;
|
|
6
|
+
}
|
|
7
|
+
.cdx-alert-primary {
|
|
8
|
+
background-color: #ebf8ff;
|
|
9
|
+
border: 1px solid #4299e1;
|
|
10
|
+
color: #2b6cb0;
|
|
11
|
+
}
|
|
12
|
+
.cdx-alert-secondary {
|
|
13
|
+
background-color: #f7fafc;
|
|
14
|
+
border: 1px solid #cbd5e0;
|
|
15
|
+
color: #222731;
|
|
16
|
+
}
|
|
17
|
+
.cdx-alert-info {
|
|
18
|
+
background-color: #e6fdff;
|
|
19
|
+
border: 1px solid #4cd4ce;
|
|
20
|
+
color: #00727c;
|
|
21
|
+
}
|
|
22
|
+
.cdx-alert-success {
|
|
23
|
+
background-color: #f0fff4;
|
|
24
|
+
border: 1px solid #68d391;
|
|
25
|
+
color: #2f855a;
|
|
26
|
+
}
|
|
27
|
+
.cdx-alert-warning {
|
|
28
|
+
background-color: #fffaf0;
|
|
29
|
+
border: 1px solid #ed8936;
|
|
30
|
+
color: #c05621;
|
|
31
|
+
}
|
|
32
|
+
.cdx-alert-danger {
|
|
33
|
+
background-color: #fff5f5;
|
|
34
|
+
border: 1px solid #fc8181;
|
|
35
|
+
color: #c53030;
|
|
36
|
+
}
|
|
37
|
+
.cdx-alert-light {
|
|
38
|
+
background-color: #fff;
|
|
39
|
+
border: 1px solid #edf2f7;
|
|
40
|
+
color: #1a202c;
|
|
41
|
+
}
|
|
42
|
+
.cdx-alert-dark {
|
|
43
|
+
background-color: #2d3748;
|
|
44
|
+
border: 1px solid #1a202c;
|
|
45
|
+
color: #d3d3d3;
|
|
46
|
+
}
|
|
47
|
+
.cdx-alert-align-left {
|
|
48
|
+
text-align: left;
|
|
49
|
+
}
|
|
50
|
+
.cdx-alert-align-center {
|
|
51
|
+
text-align: center;
|
|
52
|
+
}
|
|
53
|
+
.cdx-alert-align-right {
|
|
54
|
+
text-align: right;
|
|
55
|
+
}
|
|
56
|
+
.cdx-alert__message {
|
|
57
|
+
outline: none;
|
|
58
|
+
}
|
|
59
|
+
.cdx-alert [contentEditable='true'][data-placeholder]::before {
|
|
60
|
+
position: absolute;
|
|
61
|
+
content: attr(data-placeholder);
|
|
62
|
+
color: #707684;
|
|
63
|
+
font-weight: normal;
|
|
64
|
+
opacity: 0;
|
|
65
|
+
}
|
|
66
|
+
.cdx-alert [contentEditable='true'][data-placeholder]:empty::before {
|
|
67
|
+
opacity: 1;
|
|
68
|
+
}
|
|
69
|
+
.cdx-alert [contentEditable='true'][data-placeholder]:empty:focus::before {
|
|
70
|
+
opacity: 0;
|
|
71
|
+
}
|
|
72
|
+
.ce-popover__item[data-item-name='alert-primary'] .ce-popover__item-icon svg #background {
|
|
73
|
+
fill: #ebf8ff;
|
|
74
|
+
stroke: #4299e1;
|
|
75
|
+
}
|
|
76
|
+
.ce-popover__item[data-item-name='alert-primary'] .ce-popover__item-icon svg #content {
|
|
77
|
+
fill: #2b6cb0;
|
|
78
|
+
}
|
|
79
|
+
.ce-popover__item[data-item-name='alert-secondary'] .ce-popover__item-icon svg #background {
|
|
80
|
+
fill: #f7fafc;
|
|
81
|
+
stroke: #cbd5e0;
|
|
82
|
+
}
|
|
83
|
+
.ce-popover__item[data-item-name='alert-secondary'] .ce-popover__item-icon svg #content {
|
|
84
|
+
fill: #222731;
|
|
85
|
+
}
|
|
86
|
+
.ce-popover__item[data-item-name='alert-info'] .ce-popover__item-icon svg #background {
|
|
87
|
+
fill: #e6fdff;
|
|
88
|
+
stroke: #4cd4ce;
|
|
89
|
+
}
|
|
90
|
+
.ce-popover__item[data-item-name='alert-info'] .ce-popover__item-icon svg #content {
|
|
91
|
+
fill: #00727c;
|
|
92
|
+
}
|
|
93
|
+
.ce-popover__item[data-item-name='alert-success'] .ce-popover__item-icon svg #background {
|
|
94
|
+
fill: #f0fff4;
|
|
95
|
+
stroke: #68d391;
|
|
96
|
+
}
|
|
97
|
+
.ce-popover__item[data-item-name='alert-success'] .ce-popover__item-icon svg #content {
|
|
98
|
+
fill: #2f855a;
|
|
99
|
+
}
|
|
100
|
+
.ce-popover__item[data-item-name='alert-warning'] .ce-popover__item-icon svg #background {
|
|
101
|
+
fill: #fffaf0;
|
|
102
|
+
stroke: #ed8936;
|
|
103
|
+
}
|
|
104
|
+
.ce-popover__item[data-item-name='alert-warning'] .ce-popover__item-icon svg #content {
|
|
105
|
+
fill: #c05621;
|
|
106
|
+
}
|
|
107
|
+
.ce-popover__item[data-item-name='alert-danger'] .ce-popover__item-icon svg #background {
|
|
108
|
+
fill: #fff5f5;
|
|
109
|
+
stroke: #fc8181;
|
|
110
|
+
}
|
|
111
|
+
.ce-popover__item[data-item-name='alert-danger'] .ce-popover__item-icon svg #content {
|
|
112
|
+
fill: #c53030;
|
|
113
|
+
}
|
|
114
|
+
.ce-popover__item[data-item-name='alert-light'] .ce-popover__item-icon svg #background {
|
|
115
|
+
fill: #fff;
|
|
116
|
+
stroke: #edf2f7;
|
|
117
|
+
}
|
|
118
|
+
.ce-popover__item[data-item-name='alert-light'] .ce-popover__item-icon svg #content {
|
|
119
|
+
fill: #1a202c;
|
|
120
|
+
}
|
|
121
|
+
.ce-popover__item[data-item-name='alert-dark'] .ce-popover__item-icon svg #background {
|
|
122
|
+
fill: #2d3748;
|
|
123
|
+
stroke: #1a202c;
|
|
124
|
+
}
|
|
125
|
+
.ce-popover__item[data-item-name='alert-dark'] .ce-popover__item-icon svg #content {
|
|
126
|
+
fill: #d3d3d3;
|
|
127
|
+
}
|
|
128
|
+
|
|
129
|
+
.cdx-alert_setting__icon_wrapper {
|
|
130
|
+
display: flex;
|
|
131
|
+
flex-direction: row;
|
|
132
|
+
flex-wrap: wrap;
|
|
133
|
+
gap: 10px;
|
|
134
|
+
|
|
135
|
+
}
|
|
136
|
+
.cdx-alert_setting__icon_wrapper_align{
|
|
137
|
+
margin-top: 10px;
|
|
138
|
+
}
|
|
139
|
+
.cdx-alert_setting__icon {
|
|
140
|
+
display: inline-block;
|
|
141
|
+
width: 24px;
|
|
142
|
+
height: 24px;
|
|
143
|
+
text-align: center;
|
|
144
|
+
line-height: 24px;
|
|
145
|
+
cursor: pointer;
|
|
146
|
+
}
|
|
147
|
+
|
|
148
|
+
.cdx-alert_setting__icon_active{
|
|
149
|
+
opacity: 0.3;
|
|
150
|
+
}
|
|
@@ -0,0 +1,463 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Alert block for the Editor.js.
|
|
3
|
+
*
|
|
4
|
+
* @author Vishal Telangre
|
|
5
|
+
* @license MIT
|
|
6
|
+
*/
|
|
7
|
+
|
|
8
|
+
/**
|
|
9
|
+
* Build styles
|
|
10
|
+
*/
|
|
11
|
+
|
|
12
|
+
import type { API,BlockTool,BlockToolConstructorOptions } from "@ebl-vue/editorjs/types";
|
|
13
|
+
import './index.css';
|
|
14
|
+
|
|
15
|
+
|
|
16
|
+
|
|
17
|
+
/**
|
|
18
|
+
* Import Tool's icons
|
|
19
|
+
*/
|
|
20
|
+
const ToolboxIcon = `<?xml version="1.0" standalone="no"?><!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd"><svg t="1763693072662" class="icon" viewBox="0 0 1024 1024" version="1.1" xmlns="http://www.w3.org/2000/svg" p-id="2633" id="mx_n_1763693072663" width="24" height="24" xmlns:xlink="http://www.w3.org/1999/xlink"><path d="M83.2 147.2V448c0 25.6 19.2 44.8 44.8 44.8h768c25.6 0 44.8-19.2 44.8-44.8V147.2c0-25.6-19.2-44.8-44.8-44.8H128c-25.6 6.4-44.8 25.6-44.8 44.8z m89.6 256V192h684.8v211.2H172.8zM810.24 642.56c0-25.6-19.2-44.8-44.8-44.8h-640c-25.6 0-44.8 19.2-44.8 44.8 0 25.6 19.2 44.8 44.8 44.8h640c25.6 6.4 44.8-12.8 44.8-44.8zM554.56 866.24c0-25.6-19.2-44.8-44.8-44.8h-384c-25.6 0-44.8 19.2-44.8 44.8 0 25.6 19.2 44.8 44.8 44.8h384c25.6 6.4 44.8-12.8 44.8-44.8z" fill="#262626" p-id="2634"></path></svg>`;
|
|
21
|
+
|
|
22
|
+
|
|
23
|
+
const AlignLeftIcon = `<svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" fill="none" viewBox="0 0 24 24"><path stroke="currentColor" stroke-linecap="round" stroke-width="2" d="M17 7L5 7"/><path stroke="currentColor" stroke-linecap="round" stroke-width="2" d="M17 17H5"/><path stroke="currentColor" stroke-linecap="round" stroke-width="2" d="M13 12L5 12"/></svg>`;
|
|
24
|
+
|
|
25
|
+
const AlignCenterIcon = `<svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" fill="none" viewBox="0 0 24 24"><path stroke="currentColor" stroke-linecap="round" stroke-width="2" d="M18 7L6 7"/><path stroke="currentColor" stroke-linecap="round" stroke-width="2" d="M18 17H6"/><path stroke="currentColor" stroke-linecap="round" stroke-width="2" d="M16 12L8 12"/></svg>`;
|
|
26
|
+
|
|
27
|
+
const AlignRightIcon =`<svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" fill="none" viewBox="0 0 24 24"><path stroke="currentColor" stroke-linecap="round" stroke-width="2" d="M19 7L7 7"/><path stroke="currentColor" stroke-linecap="round" stroke-width="2" d="M19 17H7"/><path stroke="currentColor" stroke-linecap="round" stroke-width="2" d="M19 12L11 12"/></svg>`;
|
|
28
|
+
|
|
29
|
+
/**
|
|
30
|
+
* @class Alert
|
|
31
|
+
* @classdesc Alert Tool for Editor.js
|
|
32
|
+
* @property {AlertData} data - Alert Tool`s input and output data
|
|
33
|
+
* @property {object} api - Editor.js API instance
|
|
34
|
+
*
|
|
35
|
+
* @typedef {object} AlertData
|
|
36
|
+
* @description Alert Tool`s input and output data
|
|
37
|
+
* @property {string} type - Alert type
|
|
38
|
+
* @property {string} alignType - Alert align type
|
|
39
|
+
* @property {string} message - Alert message
|
|
40
|
+
*
|
|
41
|
+
* @typedef {object} AlertConfig
|
|
42
|
+
* @description Alert Tool`s initial configuration
|
|
43
|
+
* @property {string} defaultType - default Alert type
|
|
44
|
+
* @property {string} defaultAlignType - default align Alert type
|
|
45
|
+
* @property {string} messagePlaceholder - placeholder to show in Alert`s message input
|
|
46
|
+
*/
|
|
47
|
+
export default class Alert implements BlockTool{
|
|
48
|
+
/**
|
|
49
|
+
* Get Toolbox settings
|
|
50
|
+
*
|
|
51
|
+
* @public
|
|
52
|
+
* @returns {string}
|
|
53
|
+
*/
|
|
54
|
+
static get toolbox() {
|
|
55
|
+
return {
|
|
56
|
+
icon: ToolboxIcon,
|
|
57
|
+
title: 'Alert',
|
|
58
|
+
};
|
|
59
|
+
}
|
|
60
|
+
|
|
61
|
+
/**
|
|
62
|
+
* Allow to press Enter inside the Alert block
|
|
63
|
+
* @public
|
|
64
|
+
* @returns {boolean}
|
|
65
|
+
*/
|
|
66
|
+
static get enableLineBreaks() {
|
|
67
|
+
return true;
|
|
68
|
+
}
|
|
69
|
+
|
|
70
|
+
/**
|
|
71
|
+
* Default Alert type
|
|
72
|
+
*
|
|
73
|
+
* @public
|
|
74
|
+
* @returns {string}
|
|
75
|
+
*/
|
|
76
|
+
static get DEFAULT_TYPE() {
|
|
77
|
+
return 'info';
|
|
78
|
+
}
|
|
79
|
+
|
|
80
|
+
/**
|
|
81
|
+
* Default Alert align type
|
|
82
|
+
*
|
|
83
|
+
* @public
|
|
84
|
+
* @returns {string}
|
|
85
|
+
*/
|
|
86
|
+
static get DEFAULT_ALIGN_TYPE() {
|
|
87
|
+
return 'left';
|
|
88
|
+
}
|
|
89
|
+
|
|
90
|
+
/**
|
|
91
|
+
* Default placeholder for Alert message
|
|
92
|
+
*
|
|
93
|
+
* @public
|
|
94
|
+
* @returns {string}
|
|
95
|
+
*/
|
|
96
|
+
static get DEFAULT_MESSAGE_PLACEHOLDER() {
|
|
97
|
+
return 'Type here...';
|
|
98
|
+
}
|
|
99
|
+
|
|
100
|
+
/**
|
|
101
|
+
* Supported Alert types
|
|
102
|
+
*
|
|
103
|
+
* @public
|
|
104
|
+
* @returns {array}
|
|
105
|
+
*/
|
|
106
|
+
static get ALERT_TYPES() {
|
|
107
|
+
return [
|
|
108
|
+
'primary',
|
|
109
|
+
'secondary',
|
|
110
|
+
'info',
|
|
111
|
+
'success',
|
|
112
|
+
'warning',
|
|
113
|
+
'danger',
|
|
114
|
+
'light',
|
|
115
|
+
'dark',
|
|
116
|
+
];
|
|
117
|
+
}
|
|
118
|
+
|
|
119
|
+
/**
|
|
120
|
+
* Supported Align types
|
|
121
|
+
*
|
|
122
|
+
* @public
|
|
123
|
+
* @returns {array}
|
|
124
|
+
*/
|
|
125
|
+
static get ALIGN_TYPES() {
|
|
126
|
+
return ['left', 'center', 'right'];
|
|
127
|
+
}
|
|
128
|
+
|
|
129
|
+
/**
|
|
130
|
+
* Alert Tool`s styles
|
|
131
|
+
*
|
|
132
|
+
* @returns {Object}
|
|
133
|
+
*/
|
|
134
|
+
get CSS() {
|
|
135
|
+
return {
|
|
136
|
+
wrapper: 'cdx-alert',
|
|
137
|
+
wrapperForType: (type) => `cdx-alert-${type}`,
|
|
138
|
+
wrapperForAlignType: (alignType) => `cdx-alert-align-${alignType}`,
|
|
139
|
+
message: 'cdx-alert__message',
|
|
140
|
+
};
|
|
141
|
+
}
|
|
142
|
+
private alertTypes: string[];
|
|
143
|
+
private defaultType: string;
|
|
144
|
+
private defaultAlign: string;
|
|
145
|
+
private messagePlaceholder: string;
|
|
146
|
+
private data: any;
|
|
147
|
+
private api: API;
|
|
148
|
+
|
|
149
|
+
/**
|
|
150
|
+
* Render plugin`s main Element and fill it with saved data
|
|
151
|
+
*
|
|
152
|
+
* @param {AlertData} data — previously saved data
|
|
153
|
+
* @param {AlertConfig} config — user config for Tool
|
|
154
|
+
* @param {Object} api - Editor.js API
|
|
155
|
+
* @param {boolean} readOnly - read only mode flag
|
|
156
|
+
*/
|
|
157
|
+
constructor({ data, config, api, readOnly }:BlockToolConstructorOptions) {
|
|
158
|
+
this.api = api;
|
|
159
|
+
|
|
160
|
+
this.alertTypes = config.alertTypes || Alert.ALERT_TYPES;
|
|
161
|
+
this.defaultType = config.defaultType || Alert.DEFAULT_TYPE;
|
|
162
|
+
this.defaultAlign = config.defaultAlign || Alert.DEFAULT_ALIGN_TYPE;
|
|
163
|
+
this.messagePlaceholder =
|
|
164
|
+
config.messagePlaceholder || Alert.DEFAULT_MESSAGE_PLACEHOLDER;
|
|
165
|
+
|
|
166
|
+
this.data = {
|
|
167
|
+
type: this.alertTypes.includes(data.type)
|
|
168
|
+
? data.type
|
|
169
|
+
: this.defaultType,
|
|
170
|
+
align: Alert.ALIGN_TYPES.includes(data.align)
|
|
171
|
+
? data.align
|
|
172
|
+
: this.defaultAlign,
|
|
173
|
+
message: data.message || '',
|
|
174
|
+
};
|
|
175
|
+
|
|
176
|
+
this.container = undefined;
|
|
177
|
+
|
|
178
|
+
this.readOnly = readOnly;
|
|
179
|
+
}
|
|
180
|
+
|
|
181
|
+
/**
|
|
182
|
+
* Returns true to notify the core that read-only mode is supported
|
|
183
|
+
*
|
|
184
|
+
* @return {boolean}
|
|
185
|
+
*/
|
|
186
|
+
static get isReadOnlySupported() {
|
|
187
|
+
return true;
|
|
188
|
+
}
|
|
189
|
+
|
|
190
|
+
/**
|
|
191
|
+
* Create Alert Tool container
|
|
192
|
+
*
|
|
193
|
+
* @returns {Element}
|
|
194
|
+
*/
|
|
195
|
+
render() {
|
|
196
|
+
const containerClasses = [
|
|
197
|
+
this.CSS.wrapper,
|
|
198
|
+
this.CSS.wrapperForType(this.data.type),
|
|
199
|
+
this.CSS.wrapperForAlignType(this.data.align),
|
|
200
|
+
];
|
|
201
|
+
|
|
202
|
+
this.container = this._make('div', containerClasses);
|
|
203
|
+
|
|
204
|
+
const messageEl = this._make('div', [this.CSS.message], {
|
|
205
|
+
contentEditable: !this.readOnly,
|
|
206
|
+
innerHTML: this.data.message,
|
|
207
|
+
});
|
|
208
|
+
|
|
209
|
+
messageEl.dataset.placeholder = this.messagePlaceholder;
|
|
210
|
+
|
|
211
|
+
this.container.appendChild(messageEl);
|
|
212
|
+
|
|
213
|
+
return this.container;
|
|
214
|
+
}
|
|
215
|
+
_getSettingIconStyle(type: string) {
|
|
216
|
+
let classname = "";
|
|
217
|
+
switch (type) {
|
|
218
|
+
case 'primary':
|
|
219
|
+
classname = "cdx-alert-primary";
|
|
220
|
+
break;
|
|
221
|
+
case 'secondary':
|
|
222
|
+
classname = "cdx-alert-secondary";
|
|
223
|
+
break;
|
|
224
|
+
case 'info':
|
|
225
|
+
classname = "cdx-alert-info";
|
|
226
|
+
break;
|
|
227
|
+
case 'success':
|
|
228
|
+
classname = "cdx-alert-success";
|
|
229
|
+
break;
|
|
230
|
+
case 'warning':
|
|
231
|
+
classname = "cdx-alert-warning";
|
|
232
|
+
break;
|
|
233
|
+
case 'danger':
|
|
234
|
+
classname = "cdx-alert-danger";
|
|
235
|
+
break;
|
|
236
|
+
case 'light':
|
|
237
|
+
classname = "cdx-alert-light";
|
|
238
|
+
break;
|
|
239
|
+
case 'dark':
|
|
240
|
+
classname = "cdx-alert-dark";
|
|
241
|
+
break;
|
|
242
|
+
}
|
|
243
|
+
const iconWrap = this._make('div', ['cdx-alert_setting__icon',classname], {});
|
|
244
|
+
return iconWrap;
|
|
245
|
+
}
|
|
246
|
+
|
|
247
|
+
/**
|
|
248
|
+
* Create Block's settings block
|
|
249
|
+
*
|
|
250
|
+
* @returns {array}
|
|
251
|
+
*/
|
|
252
|
+
renderSettings() {
|
|
253
|
+
const wrapper = document.createElement('div');
|
|
254
|
+
const alertWrapper = document.createElement('div');
|
|
255
|
+
const alignWrapper= document.createElement('div');
|
|
256
|
+
alertWrapper.classList.add('cdx-alert_setting__icon_wrapper');
|
|
257
|
+
alignWrapper.classList.add('cdx-alert_setting__icon_wrapper');
|
|
258
|
+
alignWrapper.classList.add("cdx-alert_setting__icon_wrapper_align");
|
|
259
|
+
|
|
260
|
+
this.alertTypes.map((type) => {
|
|
261
|
+
let button = this._getSettingIconStyle(type);
|
|
262
|
+
button.setAttribute('data-type', type);
|
|
263
|
+
|
|
264
|
+
this.api.tooltip.onHover(button, this.api.i18n.t(`alert-${type}`), {
|
|
265
|
+
placement: 'top',
|
|
266
|
+
});
|
|
267
|
+
button.innerText = "A";
|
|
268
|
+
alertWrapper.appendChild(button);
|
|
269
|
+
return button;
|
|
270
|
+
}).forEach((button, index, buttons) => {
|
|
271
|
+
const type = button.getAttribute('data-type');
|
|
272
|
+
button.addEventListener('click', () => {
|
|
273
|
+
this._changeAlertType(type);
|
|
274
|
+
buttons.forEach((el, index) => {
|
|
275
|
+
const elType= el.getAttribute('data-type');
|
|
276
|
+
el.classList.toggle("cdx-alert_setting__icon_active", elType === this.data.type);
|
|
277
|
+
});
|
|
278
|
+
});
|
|
279
|
+
|
|
280
|
+
|
|
281
|
+
});
|
|
282
|
+
|
|
283
|
+
|
|
284
|
+
Alert.ALIGN_TYPES.map((align) => {
|
|
285
|
+
let button;
|
|
286
|
+
if (align === "left") {
|
|
287
|
+
button = document.createElement("div");
|
|
288
|
+
button.classList.add("cdx-alert_setting__icon");
|
|
289
|
+
button.innerHTML = AlignLeftIcon;
|
|
290
|
+
}
|
|
291
|
+
if (align === "right") {
|
|
292
|
+
button = document.createElement("div");
|
|
293
|
+
button.classList.add("cdx-alert_setting__icon");
|
|
294
|
+
button.innerHTML = AlignRightIcon;
|
|
295
|
+
|
|
296
|
+
}
|
|
297
|
+
if (align === "center") {
|
|
298
|
+
button = document.createElement("div");
|
|
299
|
+
button.classList.add("cdx-alert_setting__icon");
|
|
300
|
+
button.innerHTML = AlignCenterIcon;
|
|
301
|
+
|
|
302
|
+
|
|
303
|
+
}
|
|
304
|
+
|
|
305
|
+
button?.setAttribute("data-align", align);
|
|
306
|
+
this.api.tooltip.onHover(button!, this.api.i18n.t(`align-${align}`), {
|
|
307
|
+
placement: 'top',
|
|
308
|
+
});
|
|
309
|
+
alignWrapper.appendChild(button!);
|
|
310
|
+
return button;
|
|
311
|
+
}).forEach((button, index, buttons) => {
|
|
312
|
+
const align = button!.getAttribute('data-align');
|
|
313
|
+
button!.addEventListener('click', () => {
|
|
314
|
+
this._changeAlignType(align);
|
|
315
|
+
buttons.forEach((el, index) => {
|
|
316
|
+
const elAlign = el?.getAttribute('data-align');
|
|
317
|
+
el?.classList.toggle("cdx-alert_setting__icon_active", elAlign === this.data.align);
|
|
318
|
+
});
|
|
319
|
+
});
|
|
320
|
+
});
|
|
321
|
+
|
|
322
|
+
wrapper.appendChild(alertWrapper);
|
|
323
|
+
wrapper.appendChild(alignWrapper);
|
|
324
|
+
return wrapper;
|
|
325
|
+
}
|
|
326
|
+
|
|
327
|
+
/**
|
|
328
|
+
* Helper for formatting Alert Type / Align Type
|
|
329
|
+
*
|
|
330
|
+
* @param {string} type - Alert type or Align type
|
|
331
|
+
* @returns {string}
|
|
332
|
+
*/
|
|
333
|
+
_getFormattedName(name) {
|
|
334
|
+
return this.api.i18n.t(name.charAt(0).toUpperCase() + name.slice(1));
|
|
335
|
+
}
|
|
336
|
+
|
|
337
|
+
/**
|
|
338
|
+
* Helper for changing style of Alert block with the selected Alert type
|
|
339
|
+
*
|
|
340
|
+
* @param {string} newType - new Alert type to be applied to the block
|
|
341
|
+
* @private
|
|
342
|
+
*/
|
|
343
|
+
_changeAlertType(newType) {
|
|
344
|
+
// Save new type
|
|
345
|
+
this.data.type = newType;
|
|
346
|
+
|
|
347
|
+
this.alertTypes.forEach((type) => {
|
|
348
|
+
const alertClass = this.CSS.wrapperForType(type);
|
|
349
|
+
|
|
350
|
+
// Remove the old Alert type class
|
|
351
|
+
this.container.classList.remove(alertClass);
|
|
352
|
+
|
|
353
|
+
if (newType === type) {
|
|
354
|
+
// Add an Alert class for the selected Alert type
|
|
355
|
+
this.container.classList.add(alertClass);
|
|
356
|
+
}
|
|
357
|
+
});
|
|
358
|
+
}
|
|
359
|
+
|
|
360
|
+
/**
|
|
361
|
+
* Helper for changing align of Alert block with the selected Align type
|
|
362
|
+
*
|
|
363
|
+
* @param {string} newAlign - new align type to be applied to the block
|
|
364
|
+
* @private
|
|
365
|
+
*/
|
|
366
|
+
_changeAlignType(newAlign) {
|
|
367
|
+
// Save new type
|
|
368
|
+
this.data.align = newAlign;
|
|
369
|
+
|
|
370
|
+
Alert.ALIGN_TYPES.forEach((align) => {
|
|
371
|
+
const alignClass = this.CSS.wrapperForAlignType(align);
|
|
372
|
+
|
|
373
|
+
// Remove the old Alert type class
|
|
374
|
+
this.container.classList.remove(alignClass);
|
|
375
|
+
|
|
376
|
+
if (newAlign === align) {
|
|
377
|
+
// Add an Alert class for the selected Alert type
|
|
378
|
+
this.container.classList.add(alignClass);
|
|
379
|
+
}
|
|
380
|
+
});
|
|
381
|
+
}
|
|
382
|
+
|
|
383
|
+
/**
|
|
384
|
+
* Extract Alert data from Alert Tool element
|
|
385
|
+
*
|
|
386
|
+
* @param {HTMLDivElement} alertElement - element to save
|
|
387
|
+
* @returns {AlertData}
|
|
388
|
+
*/
|
|
389
|
+
save(alertElement) {
|
|
390
|
+
const messageEl = alertElement.querySelector(`.${this.CSS.message}`);
|
|
391
|
+
|
|
392
|
+
return { ...this.data, message: messageEl.innerHTML };
|
|
393
|
+
}
|
|
394
|
+
|
|
395
|
+
/**
|
|
396
|
+
* Helper for making Elements with attributes
|
|
397
|
+
*
|
|
398
|
+
* @param {string} tagName - new Element tag name
|
|
399
|
+
* @param {array|string} classNames - list or name of CSS classname(s)
|
|
400
|
+
* @param {Object} attributes - any attributes
|
|
401
|
+
* @returns {Element}
|
|
402
|
+
* @private
|
|
403
|
+
*/
|
|
404
|
+
_make(tagName, classNames = null, attributes = {}) {
|
|
405
|
+
let el = document.createElement(tagName);
|
|
406
|
+
|
|
407
|
+
if (Array.isArray(classNames)) {
|
|
408
|
+
el.classList.add(...classNames);
|
|
409
|
+
} else if (classNames) {
|
|
410
|
+
el.classList.add(classNames);
|
|
411
|
+
}
|
|
412
|
+
|
|
413
|
+
for (let attrName in attributes) {
|
|
414
|
+
el[attrName] = attributes[attrName];
|
|
415
|
+
}
|
|
416
|
+
|
|
417
|
+
return el;
|
|
418
|
+
}
|
|
419
|
+
|
|
420
|
+
/**
|
|
421
|
+
* Fill Alert's message with the pasted content
|
|
422
|
+
*
|
|
423
|
+
* @param {PasteEvent} event - event with pasted content
|
|
424
|
+
*/
|
|
425
|
+
onPaste(event) {
|
|
426
|
+
const { data } = event.detail;
|
|
427
|
+
|
|
428
|
+
this.data = {
|
|
429
|
+
type: this.defaultType,
|
|
430
|
+
message: data.innerHTML || '',
|
|
431
|
+
};
|
|
432
|
+
}
|
|
433
|
+
|
|
434
|
+
/**
|
|
435
|
+
* Allow Alert to be converted to/from other blocks
|
|
436
|
+
*/
|
|
437
|
+
static get conversionConfig() {
|
|
438
|
+
return {
|
|
439
|
+
// export Alert's message for other blocks
|
|
440
|
+
export: (data) => data.message,
|
|
441
|
+
// fill Alert's message from other block's export string
|
|
442
|
+
import: (string) => {
|
|
443
|
+
return {
|
|
444
|
+
message: string,
|
|
445
|
+
type: this.DEFAULT_TYPE,
|
|
446
|
+
alignType: this.DEFAULT_ALIGN_TYPE,
|
|
447
|
+
};
|
|
448
|
+
},
|
|
449
|
+
};
|
|
450
|
+
}
|
|
451
|
+
|
|
452
|
+
/**
|
|
453
|
+
* Sanitizer config for Alert Tool saved data
|
|
454
|
+
* @returns {Object}
|
|
455
|
+
*/
|
|
456
|
+
static get sanitize() {
|
|
457
|
+
return {
|
|
458
|
+
message: true,
|
|
459
|
+
type: false,
|
|
460
|
+
alignType: false,
|
|
461
|
+
};
|
|
462
|
+
}
|
|
463
|
+
}
|