@pie-lib/editable-html 9.5.13 → 10.0.0-beta.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +0 -302
- package/lib/components.js +116 -0
- package/lib/components.js.map +1 -0
- package/lib/editor.js +418 -103
- package/lib/editor.js.map +1 -1
- package/lib/index.js +101 -155
- package/lib/index.js.map +1 -1
- package/lib/new-serialization.js +320 -0
- package/lib/new-serialization.js.map +1 -0
- package/lib/old-serialization.js +330 -0
- package/lib/parse-html.js +1 -1
- package/lib/parse-html.js.map +1 -1
- package/lib/plugins/characters/custom-popper.js +1 -1
- package/lib/plugins/characters/custom-popper.js.map +1 -1
- package/lib/plugins/characters/index.js +21 -19
- package/lib/plugins/characters/index.js.map +1 -1
- package/lib/plugins/characters/utils.js +1 -1
- package/lib/plugins/characters/utils.js.map +1 -1
- package/lib/plugins/hotKeys/index.js +67 -0
- package/lib/plugins/hotKeys/index.js.map +1 -0
- package/lib/plugins/image/alt-dialog.js +1 -6
- package/lib/plugins/image/alt-dialog.js.map +1 -1
- package/lib/plugins/image/component.js +70 -53
- package/lib/plugins/image/component.js.map +1 -1
- package/lib/plugins/image/image-toolbar.js +7 -9
- package/lib/plugins/image/image-toolbar.js.map +1 -1
- package/lib/plugins/image/index.js +83 -27
- package/lib/plugins/image/index.js.map +1 -1
- package/lib/plugins/image/insert-image-handler.js +72 -33
- package/lib/plugins/image/insert-image-handler.js.map +1 -1
- package/lib/plugins/index.js +23 -41
- package/lib/plugins/index.js.map +1 -1
- package/lib/plugins/list/index.js +64 -100
- package/lib/plugins/list/index.js.map +1 -1
- package/lib/plugins/math/index.js +86 -60
- package/lib/plugins/math/index.js.map +1 -1
- package/lib/plugins/media/index.js +202 -132
- package/lib/plugins/media/index.js.map +1 -1
- package/lib/plugins/media/media-dialog.js +17 -16
- package/lib/plugins/media/media-dialog.js.map +1 -1
- package/lib/plugins/media/media-toolbar.js +3 -3
- package/lib/plugins/media/media-toolbar.js.map +1 -1
- package/lib/plugins/media/media-wrapper.js +21 -58
- package/lib/plugins/media/media-wrapper.js.map +1 -1
- package/lib/plugins/respArea/drag-in-the-blank/choice.js +3 -3
- package/lib/plugins/respArea/drag-in-the-blank/choice.js.map +1 -1
- package/lib/plugins/respArea/drag-in-the-blank/index.js +3 -2
- package/lib/plugins/respArea/drag-in-the-blank/index.js.map +1 -1
- package/lib/plugins/respArea/explicit-constructed-response/index.js +3 -2
- package/lib/plugins/respArea/explicit-constructed-response/index.js.map +1 -1
- package/lib/plugins/respArea/icons/index.js +13 -15
- package/lib/plugins/respArea/icons/index.js.map +1 -1
- package/lib/plugins/respArea/index.js +87 -53
- package/lib/plugins/respArea/index.js.map +1 -1
- package/lib/plugins/respArea/inline-dropdown/index.js +4 -3
- package/lib/plugins/respArea/inline-dropdown/index.js.map +1 -1
- package/lib/plugins/respArea/utils.js +17 -20
- package/lib/plugins/respArea/utils.js.map +1 -1
- package/lib/plugins/table/icons/index.js +1 -1
- package/lib/plugins/table/icons/index.js.map +1 -1
- package/lib/plugins/table/index.js +381 -212
- package/lib/plugins/table/index.js.map +1 -1
- package/lib/plugins/table/table-toolbar.js +5 -6
- package/lib/plugins/table/table-toolbar.js.map +1 -1
- package/lib/plugins/toolbar/default-toolbar.js +55 -11
- package/lib/plugins/toolbar/default-toolbar.js.map +1 -1
- package/lib/plugins/toolbar/done-button.js +1 -1
- package/lib/plugins/toolbar/done-button.js.map +1 -1
- package/lib/plugins/toolbar/editor-and-toolbar.js +186 -232
- package/lib/plugins/toolbar/editor-and-toolbar.js.map +1 -1
- package/lib/plugins/toolbar/index.js +1 -2
- package/lib/plugins/toolbar/index.js.map +1 -1
- package/lib/plugins/toolbar/toolbar-buttons.js +1 -1
- package/lib/plugins/toolbar/toolbar-buttons.js.map +1 -1
- package/lib/plugins/toolbar/toolbar.js +253 -239
- package/lib/plugins/toolbar/toolbar.js.map +1 -1
- package/lib/plugins/utils.js +27 -2
- package/lib/plugins/utils.js.map +1 -1
- package/lib/serialization.js +1 -1
- package/lib/serialization.js.map +1 -1
- package/lib/slate-editor.js +302 -0
- package/lib/test-serializer.js +189 -0
- package/lib/test-serializer.js.map +1 -0
- package/lib/theme.js +1 -1
- package/lib/theme.js.map +1 -1
- package/package.json +18 -14
- package/playground/image/data.js +20 -20
- package/playground/image/index.html +22 -20
- package/playground/image/index.jsx +12 -10
- package/playground/index.html +25 -23
- package/playground/mathquill/index.html +23 -20
- package/playground/mathquill/index.jsx +18 -22
- package/playground/prod-test/index.html +24 -20
- package/playground/prod-test/index.jsx +5 -3
- package/playground/schema-override/data.js +10 -10
- package/playground/schema-override/image-plugin.jsx +3 -4
- package/playground/schema-override/index.html +21 -19
- package/playground/schema-override/index.jsx +13 -14
- package/playground/serialization/data.js +10 -10
- package/playground/serialization/image-plugin.jsx +3 -4
- package/playground/serialization/index.html +22 -20
- package/playground/table-examples.html +5 -8
- package/playground/webpack.config.js +10 -10
- package/src/components.js +135 -0
- package/src/editor.jsx +478 -141
- package/src/index.jsx +71 -95
- package/src/new-serialization.jsx +291 -0
- package/src/parse-html.js +1 -1
- package/src/plugins/characters/custom-popper.js +7 -7
- package/src/plugins/characters/index.jsx +33 -34
- package/src/plugins/characters/utils.js +81 -81
- package/src/plugins/hotKeys/index.js +54 -0
- package/src/plugins/image/alt-dialog.jsx +4 -5
- package/src/plugins/image/component.jsx +106 -89
- package/src/plugins/image/image-toolbar.jsx +27 -19
- package/src/plugins/image/index.jsx +75 -43
- package/src/plugins/image/insert-image-handler.js +62 -27
- package/src/plugins/index.jsx +23 -41
- package/src/plugins/list/index.jsx +70 -95
- package/src/plugins/math/index.jsx +102 -82
- package/src/plugins/media/index.jsx +159 -124
- package/src/plugins/media/media-dialog.js +98 -71
- package/src/plugins/media/media-toolbar.jsx +8 -8
- package/src/plugins/media/media-wrapper.jsx +29 -30
- package/src/plugins/respArea/drag-in-the-blank/choice.jsx +21 -19
- package/src/plugins/respArea/drag-in-the-blank/index.jsx +14 -11
- package/src/plugins/respArea/explicit-constructed-response/index.jsx +7 -6
- package/src/plugins/respArea/icons/index.jsx +11 -14
- package/src/plugins/respArea/index.jsx +92 -52
- package/src/plugins/respArea/inline-dropdown/index.jsx +9 -8
- package/src/plugins/respArea/utils.jsx +26 -35
- package/src/plugins/table/icons/index.jsx +17 -11
- package/src/plugins/table/index.jsx +288 -231
- package/src/plugins/table/table-toolbar.jsx +15 -11
- package/src/plugins/toolbar/default-toolbar.jsx +65 -19
- package/src/plugins/toolbar/done-button.jsx +4 -4
- package/src/plugins/toolbar/editor-and-toolbar.jsx +150 -145
- package/src/plugins/toolbar/index.jsx +2 -3
- package/src/plugins/toolbar/toolbar-buttons.jsx +11 -11
- package/src/plugins/toolbar/toolbar.jsx +244 -221
- package/src/plugins/utils.js +21 -4
- package/src/serialization.jsx +32 -32
- package/src/test-serializer.js +139 -0
- package/src/test-serializer.js.rej +20 -0
|
@@ -1,64 +1,90 @@
|
|
|
1
|
-
import
|
|
1
|
+
import React from 'react';
|
|
2
|
+
import debug from 'debug';
|
|
3
|
+
import get from 'lodash/get';
|
|
4
|
+
import { Data, Editor, Inline, Node as SlateNode } from 'slate';
|
|
2
5
|
|
|
3
6
|
import Image from '@material-ui/icons/Image';
|
|
4
7
|
import ImageComponent from './component';
|
|
5
8
|
import ImageToolbar from './image-toolbar';
|
|
6
9
|
import InsertImageHandler from './insert-image-handler';
|
|
7
|
-
import React from 'react';
|
|
8
|
-
import debug from 'debug';
|
|
9
10
|
|
|
10
11
|
const log = debug('@pie-lib:editable-html:plugins:image');
|
|
11
12
|
|
|
13
|
+
const getNodeBy = (editor, callback) => {
|
|
14
|
+
const descendants = SlateNode.descendants(editor, {
|
|
15
|
+
reverse: true
|
|
16
|
+
});
|
|
17
|
+
|
|
18
|
+
for (const [descendant, descendantPath] of descendants) {
|
|
19
|
+
if (callback(descendant, descendantPath)) {
|
|
20
|
+
return [descendant, descendantPath];
|
|
21
|
+
}
|
|
22
|
+
}
|
|
23
|
+
};
|
|
24
|
+
|
|
12
25
|
export default function ImagePlugin(opts) {
|
|
13
26
|
const toolbar = opts.insertImageRequested && {
|
|
14
27
|
icon: <Image />,
|
|
15
|
-
onClick:
|
|
28
|
+
onClick: editor => {
|
|
16
29
|
log('[toolbar] onClick');
|
|
17
|
-
const inline =
|
|
30
|
+
const inline = {
|
|
18
31
|
type: 'image',
|
|
19
|
-
isVoid: true,
|
|
20
32
|
data: {
|
|
33
|
+
newImage: true,
|
|
21
34
|
loaded: false,
|
|
22
|
-
src: undefined
|
|
35
|
+
src: undefined
|
|
23
36
|
},
|
|
24
|
-
|
|
37
|
+
children: [{ text: '' }]
|
|
38
|
+
};
|
|
39
|
+
|
|
40
|
+
editor.insertNode(inline);
|
|
41
|
+
|
|
42
|
+
const [node, nodePath] = getNodeBy(
|
|
43
|
+
editor,
|
|
44
|
+
descendant => descendant.type === 'image' && get(descendant, 'data.newImage')
|
|
45
|
+
);
|
|
25
46
|
|
|
26
|
-
|
|
27
|
-
onChange(change);
|
|
28
|
-
opts.insertImageRequested((getValue) => new InsertImageHandler(inline, getValue, onChange));
|
|
47
|
+
opts.insertImageRequested(() => new InsertImageHandler(node, nodePath, editor));
|
|
29
48
|
},
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
const
|
|
33
|
-
const
|
|
34
|
-
const
|
|
35
|
-
const onChange = (newValues, done) => {
|
|
49
|
+
customToolbar: (node, value, editor, onToolbarDone) => {
|
|
50
|
+
const alignment = node.data.alignment;
|
|
51
|
+
const alt = node.data.alt;
|
|
52
|
+
const imageLoaded = node.data.loaded !== false;
|
|
53
|
+
const onChange = newValues => {
|
|
36
54
|
const update = {
|
|
37
55
|
...node.data.toObject(),
|
|
38
|
-
...newValues
|
|
56
|
+
...newValues
|
|
39
57
|
};
|
|
40
58
|
|
|
41
59
|
const change = value.change().setNodeByKey(node.key, { data: update });
|
|
42
|
-
onToolbarDone(change,
|
|
60
|
+
onToolbarDone(change, false);
|
|
43
61
|
};
|
|
44
62
|
|
|
45
63
|
const Tb = () => (
|
|
46
|
-
<ImageToolbar
|
|
47
|
-
disableImageAlignmentButtons={opts.disableImageAlignmentButtons}
|
|
48
|
-
alt={alt}
|
|
49
|
-
imageLoaded={imageLoaded}
|
|
50
|
-
alignment={alignment || 'left'}
|
|
51
|
-
onChange={onChange}
|
|
52
|
-
/>
|
|
64
|
+
<ImageToolbar alt={alt} imageLoaded={imageLoaded} alignment={alignment || 'left'} onChange={onChange} />
|
|
53
65
|
);
|
|
54
66
|
return Tb;
|
|
55
67
|
},
|
|
56
|
-
showDone: true
|
|
68
|
+
showDone: true
|
|
57
69
|
};
|
|
58
70
|
|
|
59
71
|
return {
|
|
60
72
|
name: 'image',
|
|
61
73
|
toolbar,
|
|
74
|
+
rules: editor => {
|
|
75
|
+
const { isVoid, isInline } = editor;
|
|
76
|
+
|
|
77
|
+
editor.isVoid = element => {
|
|
78
|
+
return element.type === 'image' ? true : isVoid(element);
|
|
79
|
+
};
|
|
80
|
+
|
|
81
|
+
editor.isInline = element => {
|
|
82
|
+
return element.type === 'image' ? true : isInline(element);
|
|
83
|
+
};
|
|
84
|
+
|
|
85
|
+
return editor;
|
|
86
|
+
},
|
|
87
|
+
supports: node => node.type === 'image',
|
|
62
88
|
deleteNode: (e, node, value, onChange) => {
|
|
63
89
|
e.preventDefault();
|
|
64
90
|
if (opts.onDelete) {
|
|
@@ -72,7 +98,9 @@ export default function ImagePlugin(opts) {
|
|
|
72
98
|
change = v.change().removeNodeByKey(node.key);
|
|
73
99
|
} else {
|
|
74
100
|
log('[error]: ', err);
|
|
75
|
-
change = v
|
|
101
|
+
change = v
|
|
102
|
+
.change()
|
|
103
|
+
.setNodeByKey(node.key, node.data.merge(Data.create({ deleteStatus: 'failed' })));
|
|
76
104
|
}
|
|
77
105
|
onChange(change);
|
|
78
106
|
});
|
|
@@ -81,8 +109,8 @@ export default function ImagePlugin(opts) {
|
|
|
81
109
|
onChange(change);
|
|
82
110
|
}
|
|
83
111
|
},
|
|
84
|
-
stopReset:
|
|
85
|
-
const imgPendingInsertion = value.document.findDescendant(
|
|
112
|
+
stopReset: value => {
|
|
113
|
+
const imgPendingInsertion = value.document.findDescendant(n => {
|
|
86
114
|
if (n.type !== 'image') {
|
|
87
115
|
return;
|
|
88
116
|
}
|
|
@@ -99,21 +127,25 @@ export default function ImagePlugin(opts) {
|
|
|
99
127
|
onFocus: opts.onFocus,
|
|
100
128
|
onBlur: opts.onBlur,
|
|
101
129
|
maxImageWidth: opts.maxImageWidth,
|
|
102
|
-
maxImageHeight: opts.maxImageHeight
|
|
130
|
+
maxImageHeight: opts.maxImageHeight
|
|
103
131
|
},
|
|
104
|
-
props
|
|
132
|
+
props
|
|
133
|
+
);
|
|
134
|
+
return (
|
|
135
|
+
<ImageComponent {...all}>
|
|
136
|
+
{props.children}
|
|
137
|
+
</ImageComponent>
|
|
105
138
|
);
|
|
106
|
-
return <ImageComponent {...all} />;
|
|
107
139
|
}
|
|
108
140
|
},
|
|
109
|
-
normalizeNode:
|
|
141
|
+
normalizeNode: node => {
|
|
110
142
|
const textNodeMap = {};
|
|
111
143
|
const updateNodesArray = [];
|
|
112
144
|
let index = 0;
|
|
113
145
|
|
|
114
146
|
if (node.object !== 'document') return;
|
|
115
147
|
|
|
116
|
-
node.findDescendant(
|
|
148
|
+
node.findDescendant(d => {
|
|
117
149
|
if (d.object === 'text') {
|
|
118
150
|
textNodeMap[index] = d;
|
|
119
151
|
}
|
|
@@ -129,12 +161,12 @@ export default function ImagePlugin(opts) {
|
|
|
129
161
|
|
|
130
162
|
if (!updateNodesArray.length) return;
|
|
131
163
|
|
|
132
|
-
return
|
|
164
|
+
return change => {
|
|
133
165
|
change.withoutNormalization(() => {
|
|
134
|
-
updateNodesArray.forEach(
|
|
166
|
+
updateNodesArray.forEach(n => change.insertTextByKey(n.key, 0, ' '));
|
|
135
167
|
});
|
|
136
168
|
};
|
|
137
|
-
}
|
|
169
|
+
}
|
|
138
170
|
};
|
|
139
171
|
}
|
|
140
172
|
|
|
@@ -159,8 +191,8 @@ export const serialization = {
|
|
|
159
191
|
margin: el.style.margin,
|
|
160
192
|
justifyContent: el.style.justifyContent,
|
|
161
193
|
alignment: el.getAttribute('alignment'),
|
|
162
|
-
alt: el.getAttribute('alt')
|
|
163
|
-
}
|
|
194
|
+
alt: el.getAttribute('alt')
|
|
195
|
+
}
|
|
164
196
|
};
|
|
165
197
|
log('return object: ', out);
|
|
166
198
|
return out;
|
|
@@ -172,7 +204,7 @@ export const serialization = {
|
|
|
172
204
|
const src = data.get('src');
|
|
173
205
|
const width = data.get('width');
|
|
174
206
|
const height = data.get('height');
|
|
175
|
-
const alignment = data.get('alignment')
|
|
207
|
+
const alignment = data.get('alignment');
|
|
176
208
|
const margin = data.get('margin');
|
|
177
209
|
const justifyContent = data.get('margin');
|
|
178
210
|
const alt = data.get('alt');
|
|
@@ -214,9 +246,9 @@ export const serialization = {
|
|
|
214
246
|
src,
|
|
215
247
|
style,
|
|
216
248
|
alignment,
|
|
217
|
-
alt
|
|
249
|
+
alt
|
|
218
250
|
};
|
|
219
251
|
|
|
220
252
|
return <img {...props} />;
|
|
221
|
-
}
|
|
253
|
+
}
|
|
222
254
|
};
|
|
@@ -1,32 +1,32 @@
|
|
|
1
|
-
import
|
|
1
|
+
import omit from 'lodash/omit';
|
|
2
2
|
import debug from 'debug';
|
|
3
3
|
|
|
4
4
|
const log = debug('@pie-lib:editable-html:image:insert-image-handler');
|
|
5
5
|
|
|
6
6
|
/**
|
|
7
7
|
* Handles user selection, insertion (or cancellation) of an image into the editor.
|
|
8
|
-
* @param {Block}
|
|
8
|
+
* @param {Block} placeHolderPath - a block that has been added to the editor as a place holder for the image
|
|
9
9
|
* @param {Function} getValue - a function to return the value of the editor
|
|
10
10
|
* @param {Function} onChange - callback to notify changes applied by the handler
|
|
11
11
|
* @param {Boolean} isPasted - a boolean that keeps track if the file is pasted
|
|
12
12
|
*/
|
|
13
13
|
class InsertImageHandler {
|
|
14
|
-
constructor(
|
|
15
|
-
this.
|
|
16
|
-
this.
|
|
17
|
-
this.
|
|
14
|
+
constructor(node, placeHolderPath, editor, isPasted = false) {
|
|
15
|
+
this.node = node;
|
|
16
|
+
this.placeHolderPath = placeHolderPath;
|
|
17
|
+
this.editor = editor;
|
|
18
18
|
this.isPasted = isPasted;
|
|
19
19
|
}
|
|
20
20
|
|
|
21
21
|
getPlaceholderInDocument(value) {
|
|
22
22
|
const { document } = value;
|
|
23
|
-
const directChild = document.getChild(this.
|
|
23
|
+
const directChild = document.getChild(this.placeHolderPath);
|
|
24
24
|
|
|
25
25
|
if (directChild) {
|
|
26
26
|
return directChild;
|
|
27
27
|
}
|
|
28
28
|
|
|
29
|
-
const child = document.getDescendant(this.
|
|
29
|
+
const child = document.getDescendant(this.placeHolderPath);
|
|
30
30
|
|
|
31
31
|
if (child) {
|
|
32
32
|
return child;
|
|
@@ -38,10 +38,10 @@ class InsertImageHandler {
|
|
|
38
38
|
|
|
39
39
|
cancel() {
|
|
40
40
|
log('insert cancelled');
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
41
|
+
this.editor.apply({
|
|
42
|
+
type: 'remove_node',
|
|
43
|
+
path: this.placeHolderPath
|
|
44
|
+
});
|
|
45
45
|
}
|
|
46
46
|
|
|
47
47
|
done(err, src) {
|
|
@@ -50,12 +50,30 @@ class InsertImageHandler {
|
|
|
50
50
|
//eslint-disable-next-line
|
|
51
51
|
console.log(err);
|
|
52
52
|
} else {
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
53
|
+
this.editor.apply({
|
|
54
|
+
type: 'set_node',
|
|
55
|
+
path: this.placeHolderPath,
|
|
56
|
+
properties: {
|
|
57
|
+
data: this.node.data
|
|
58
|
+
},
|
|
59
|
+
newProperties: {
|
|
60
|
+
data: {
|
|
61
|
+
src,
|
|
62
|
+
loaded: true,
|
|
63
|
+
percent: 100
|
|
64
|
+
}
|
|
65
|
+
}
|
|
66
|
+
});
|
|
67
|
+
const newData = {
|
|
68
|
+
...this.node.data,
|
|
69
|
+
src,
|
|
70
|
+
loaded: true,
|
|
71
|
+
percent: 100
|
|
72
|
+
};
|
|
56
73
|
|
|
57
|
-
|
|
58
|
-
|
|
74
|
+
this.node = Object.assign({}, this.node, {
|
|
75
|
+
data: omit(newData, 'newImage')
|
|
76
|
+
});
|
|
59
77
|
}
|
|
60
78
|
}
|
|
61
79
|
|
|
@@ -72,23 +90,40 @@ class InsertImageHandler {
|
|
|
72
90
|
log('[fileChosen] file: ', file);
|
|
73
91
|
const reader = new FileReader();
|
|
74
92
|
reader.onload = () => {
|
|
75
|
-
const value = this.getValue();
|
|
76
93
|
const dataURL = reader.result;
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
94
|
+
|
|
95
|
+
this.editor.apply({
|
|
96
|
+
type: 'set_node',
|
|
97
|
+
path: this.placeHolderPath,
|
|
98
|
+
properties: {
|
|
99
|
+
data: this.node.data
|
|
100
|
+
},
|
|
101
|
+
newProperties: {
|
|
102
|
+
data: {
|
|
103
|
+
...this.node.data,
|
|
104
|
+
src: dataURL
|
|
105
|
+
}
|
|
106
|
+
}
|
|
107
|
+
});
|
|
108
|
+
this.node = Object.assign({}, this.node, { data: { src: dataURL } });
|
|
81
109
|
};
|
|
82
110
|
reader.readAsDataURL(file);
|
|
83
111
|
}
|
|
84
112
|
|
|
85
113
|
progress(percent, bytes, total) {
|
|
86
114
|
log('progress: ', percent, bytes, total);
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
115
|
+
|
|
116
|
+
this.editor.apply({
|
|
117
|
+
type: 'set_node',
|
|
118
|
+
path: this.placeHolderPath,
|
|
119
|
+
properties: {
|
|
120
|
+
data: this.node.data
|
|
121
|
+
},
|
|
122
|
+
newProperties: {
|
|
123
|
+
data: { ...this.node.data, percent }
|
|
124
|
+
}
|
|
125
|
+
});
|
|
126
|
+
this.node = Object.assign({}, this.node, { data: { percent } });
|
|
92
127
|
}
|
|
93
128
|
}
|
|
94
129
|
|
package/src/plugins/index.jsx
CHANGED
|
@@ -1,3 +1,6 @@
|
|
|
1
|
+
import { withHistory } from 'slate-history';
|
|
2
|
+
import { withReact } from 'slate-react';
|
|
3
|
+
|
|
1
4
|
import Bold from '@material-ui/icons/FormatBold';
|
|
2
5
|
// import Code from '@material-ui/icons/Code';
|
|
3
6
|
import BulletedListIcon from '@material-ui/icons/FormatListBulleted';
|
|
@@ -17,43 +20,10 @@ import debug from 'debug';
|
|
|
17
20
|
import List from './list';
|
|
18
21
|
import TablePlugin from './table';
|
|
19
22
|
import RespAreaPlugin from './respArea';
|
|
23
|
+
import MarkHotkey from './hotKeys';
|
|
20
24
|
|
|
21
25
|
const log = debug('@pie-lib:editable-html:plugins');
|
|
22
26
|
|
|
23
|
-
function MarkHotkey(options) {
|
|
24
|
-
const { type, key, icon, tag } = options;
|
|
25
|
-
|
|
26
|
-
// Return our "plugin" object, containing the `onKeyDown` handler.
|
|
27
|
-
return {
|
|
28
|
-
toolbar: {
|
|
29
|
-
isMark: true,
|
|
30
|
-
type,
|
|
31
|
-
icon,
|
|
32
|
-
onToggle: (change) => {
|
|
33
|
-
log('[onToggleMark] type: ', type);
|
|
34
|
-
return change.toggleMark(type);
|
|
35
|
-
},
|
|
36
|
-
},
|
|
37
|
-
renderMark(props) {
|
|
38
|
-
if (props.mark.type === type) {
|
|
39
|
-
const K = tag || type;
|
|
40
|
-
return <K>{props.children}</K>;
|
|
41
|
-
}
|
|
42
|
-
},
|
|
43
|
-
onKeyDown(event, change) {
|
|
44
|
-
// Check that the key pressed matches our `key` option.
|
|
45
|
-
if (!event.metaKey || event.key != key) return;
|
|
46
|
-
|
|
47
|
-
// Prevent the default characters from being inserted.
|
|
48
|
-
event.preventDefault();
|
|
49
|
-
|
|
50
|
-
// Toggle the mark `type`.
|
|
51
|
-
change.toggleMark(type);
|
|
52
|
-
return true;
|
|
53
|
-
},
|
|
54
|
-
};
|
|
55
|
-
}
|
|
56
|
-
|
|
57
27
|
export const ALL_PLUGINS = [
|
|
58
28
|
'bold',
|
|
59
29
|
// 'code',
|
|
@@ -68,10 +38,10 @@ export const ALL_PLUGINS = [
|
|
|
68
38
|
'table',
|
|
69
39
|
'video',
|
|
70
40
|
'audio',
|
|
71
|
-
'responseArea'
|
|
41
|
+
'responseArea'
|
|
72
42
|
];
|
|
73
43
|
|
|
74
|
-
export const DEFAULT_PLUGINS = ALL_PLUGINS.filter(
|
|
44
|
+
export const DEFAULT_PLUGINS = ALL_PLUGINS.filter(plug => plug !== 'responseArea');
|
|
75
45
|
|
|
76
46
|
export const buildPlugins = (activePlugins, opts) => {
|
|
77
47
|
log('[buildPlugins] opts: ', opts);
|
|
@@ -82,7 +52,9 @@ export const buildPlugins = (activePlugins, opts) => {
|
|
|
82
52
|
const imagePlugin = opts.image && opts.image.onDelete && ImagePlugin(opts.image);
|
|
83
53
|
const mathPlugin = MathPlugin(opts.math);
|
|
84
54
|
const respAreaPlugin =
|
|
85
|
-
opts.responseArea &&
|
|
55
|
+
opts.responseArea &&
|
|
56
|
+
opts.responseArea.type &&
|
|
57
|
+
RespAreaPlugin(opts.responseArea, compact([mathPlugin]));
|
|
86
58
|
|
|
87
59
|
return compact([
|
|
88
60
|
addIf('table', TablePlugin(opts.table, compact([imagePlugin, mathPlugin, respAreaPlugin]))),
|
|
@@ -95,19 +67,29 @@ export const buildPlugins = (activePlugins, opts) => {
|
|
|
95
67
|
key: '~',
|
|
96
68
|
type: 'strikethrough',
|
|
97
69
|
icon: <Strikethrough />,
|
|
98
|
-
tag: 'del'
|
|
99
|
-
})
|
|
70
|
+
tag: 'del'
|
|
71
|
+
})
|
|
100
72
|
),
|
|
101
73
|
addIf('underline', MarkHotkey({ key: 'u', type: 'underline', icon: <Underline />, tag: 'u' })),
|
|
102
74
|
addIf('image', imagePlugin),
|
|
103
75
|
addIf('video', MediaPlugin('video', opts.media)),
|
|
104
76
|
addIf('audio', MediaPlugin('audio', opts.media)),
|
|
105
77
|
addIf('math', mathPlugin),
|
|
106
|
-
...opts.languageCharacters.map(
|
|
78
|
+
...opts.languageCharacters.map(config => addIf('languageCharacters', CharactersPlugin(config))),
|
|
107
79
|
addIf('bulleted-list', List({ key: 'l', type: 'ul_list', icon: <BulletedListIcon /> })),
|
|
108
80
|
addIf('numbered-list', List({ key: 'n', type: 'ol_list', icon: <NumberedListIcon /> })),
|
|
109
81
|
ToolbarPlugin(opts.toolbar),
|
|
110
82
|
SoftBreakPlugin({ shift: true }),
|
|
111
|
-
addIf('responseArea', respAreaPlugin)
|
|
83
|
+
addIf('responseArea', respAreaPlugin)
|
|
112
84
|
]);
|
|
113
85
|
};
|
|
86
|
+
|
|
87
|
+
export const withPlugins = (editor, activePlugins) => {
|
|
88
|
+
activePlugins.forEach(plugin => {
|
|
89
|
+
if (typeof plugin.rules === 'function') {
|
|
90
|
+
plugin.rules(editor);
|
|
91
|
+
}
|
|
92
|
+
});
|
|
93
|
+
|
|
94
|
+
return withHistory(withReact(editor));
|
|
95
|
+
};
|