|
1 | 1 | import attachTribute from '../tribute.js';
|
2 | 2 |
|
| 3 | +const {appSubUrl} = window.config; |
| 4 | + |
| 5 | +function loadScript(url) { |
| 6 | + return new Promise((resolve, reject) => { |
| 7 | + const script = document.createElement('script'); |
| 8 | + script.async = true; |
| 9 | + script.addEventListener('load', () => { |
| 10 | + resolve(); |
| 11 | + }); |
| 12 | + script.addEventListener('error', (e) => { |
| 13 | + reject(e.error); |
| 14 | + }); |
| 15 | + script.src = url; |
| 16 | + document.body.appendChild(script); |
| 17 | + }); |
| 18 | +} |
| 19 | + |
| 20 | +/** |
| 21 | + * @returns {EasyMDE} |
| 22 | + */ |
| 23 | +export async function importEasyMDE() { |
| 24 | + // for CodeMirror: the plugins should be loaded dynamically |
| 25 | + // https://github.com/codemirror/CodeMirror/issues/5484 |
| 26 | + // https://github.com/codemirror/CodeMirror/issues/4838 |
| 27 | + |
| 28 | + const [{default: EasyMDE}, {default: CodeMirror}] = await Promise.all([ |
| 29 | + import(/* webpackChunkName: "easymde" */'easymde'), |
| 30 | + import(/* webpackChunkName: "codemirror" */'codemirror'), |
| 31 | + import(/* webpackChunkName: "easymde" */'easymde/dist/easymde.min.css'), |
| 32 | + ]); |
| 33 | + |
| 34 | + // CodeMirror plugins must be loaded by a "Plain browser env" |
| 35 | + window.CodeMirror = CodeMirror; |
| 36 | + await Promise.all([ |
| 37 | + loadScript(`${appSubUrl}/assets/vendor/plugins/codemirror/addon/mode/loadmode.js`), |
| 38 | + loadScript(`${appSubUrl}/assets/vendor/plugins/codemirror/mode/meta.js`), |
| 39 | + ]); |
| 40 | + |
| 41 | + // the loadmode.js/meta.js would set the modeURL/modeInfo properties, so we check it to make sure our loading works |
| 42 | + if (!CodeMirror.modeURL || !CodeMirror.modeInfo) { |
| 43 | + throw new Error('failed to load plugins for CodeMirror'); |
| 44 | + } |
| 45 | + |
| 46 | + CodeMirror.modeURL = `${appSubUrl}/assets/vendor/plugins/codemirror/mode/%N/%N.js`; |
| 47 | + return EasyMDE; |
| 48 | +} |
| 49 | + |
3 | 50 | /**
|
4 | 51 | * create an EasyMDE editor for comment
|
5 | 52 | * @param textarea jQuery or HTMLElement
|
6 | 53 | * @returns {null|EasyMDE}
|
7 | 54 | */
|
8 |
| -export function createCommentEasyMDE(textarea) { |
| 55 | +export async function createCommentEasyMDE(textarea) { |
9 | 56 | if (textarea instanceof jQuery) {
|
10 | 57 | textarea = textarea[0];
|
11 | 58 | }
|
12 | 59 | if (!textarea) {
|
13 | 60 | return null;
|
14 | 61 | }
|
15 | 62 |
|
16 |
| - const easyMDE = new window.EasyMDE({ |
| 63 | + const EasyMDE = await importEasyMDE(); |
| 64 | + const easyMDE = new EasyMDE({ |
17 | 65 | autoDownloadFontAwesome: false,
|
18 | 66 | element: textarea,
|
19 | 67 | forceSync: true,
|
20 | 68 | renderingConfig: {
|
21 |
| - singleLineBreaks: false |
| 69 | + singleLineBreaks: false, |
22 | 70 | },
|
23 | 71 | indentWithTabs: false,
|
24 | 72 | tabSize: 4,
|
@@ -56,23 +104,23 @@ export function createCommentEasyMDE(textarea) {
|
56 | 104 | className: 'fa fa-file',
|
57 | 105 | title: 'Revert to simple textarea',
|
58 | 106 | },
|
59 |
| - ] |
| 107 | + ], |
60 | 108 | });
|
61 | 109 | const inputField = easyMDE.codemirror.getInputField();
|
62 | 110 | inputField.classList.add('js-quick-submit');
|
63 | 111 | easyMDE.codemirror.setOption('extraKeys', {
|
64 | 112 | Enter: () => {
|
65 | 113 | const tributeContainer = document.querySelector('.tribute-container');
|
66 | 114 | if (!tributeContainer || tributeContainer.style.display === 'none') {
|
67 |
| - return CodeMirror.Pass; |
| 115 | + return window.CodeMirror.Pass; |
68 | 116 | }
|
69 | 117 | },
|
70 | 118 | Backspace: (cm) => {
|
71 | 119 | if (cm.getInputField().trigger) {
|
72 | 120 | cm.getInputField().trigger('input');
|
73 | 121 | }
|
74 | 122 | cm.execCommand('delCharBefore');
|
75 |
| - } |
| 123 | + }, |
76 | 124 | });
|
77 | 125 | attachTribute(inputField, {mentions: true, emoji: true});
|
78 | 126 | attachEasyMDEToElements(easyMDE);
|
|
0 commit comments