Skip to content

Commit 4ec6e80

Browse files
committed
Editor default options refactoring + include imageUploader plugin
In order to use imageUploader plugin: - js/css files must included in the app; - an upload method must be provided in Active Admin entity; - the image_uploader server_url field option needs to be set.
1 parent 707f4a5 commit 4ec6e80

3 files changed

Lines changed: 91 additions & 15 deletions

File tree

app/assets/javascripts/activeadmin/quill.imageUploader.min.js

Lines changed: 1 addition & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

app/assets/javascripts/activeadmin/quill_editor_input.js

Lines changed: 57 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -1,25 +1,40 @@
1+
// --- functions ---------------------------------------------------------------
12
function initQuillEditors() {
3+
var default_theme = 'snow';
4+
var default_toolbar = [
5+
['bold', 'italic', 'underline'],
6+
['link', 'blockquote', 'code-block'],
7+
[{ 'script': 'sub'}, { 'script': 'super' }],
8+
[{ 'align': [] }, { list: 'ordered' }, { list: 'bullet' }],
9+
[{ 'color': [] }, { 'background': [] }],
10+
['image'],
11+
['clean'],
12+
];
213
var editors = document.querySelectorAll('.quill-editor');
3-
var default_options = {
4-
modules: {
5-
toolbar: [
6-
['bold', 'italic', 'underline'],
7-
['link', 'blockquote', 'code-block'],
8-
[{ 'script': 'sub'}, { 'script': 'super' }],
9-
[{ 'align': [] }, { list: 'ordered' }, { list: 'bullet' }],
10-
[{ 'color': [] }, { 'background': [] }],
11-
['clean'],
12-
]
13-
},
14-
placeholder: '',
15-
theme: 'snow'
16-
};
14+
var registered_plugins = {};
1715

1816
for(var i = 0; i < editors.length; i++) {
1917
var content = editors[i].querySelector('.quill-editor-content');
2018
var isActive = editors[i].classList.contains('quill-editor--active');
2119
if(content && !isActive) {
22-
var options = editors[i].getAttribute('data-options') ? JSON.parse(editors[i].getAttribute('data-options')) : default_options;
20+
// Setup editor options
21+
var options = editors[i].getAttribute('data-options') ? JSON.parse(editors[i].getAttribute('data-options')) : {};
22+
if(!options.theme) options.theme = default_theme;
23+
if(!options.modules) options.modules = {};
24+
if(!options.modules.toolbar) options.modules.toolbar = default_toolbar;
25+
26+
// Setup plugin options
27+
var plugin_options = editors[i].getAttribute('data-plugins') ? JSON.parse(editors[i].getAttribute('data-plugins')) : {};
28+
if(plugin_options.image_uploader && plugin_options.image_uploader.server_url) {
29+
if(!registered_plugins.image_uploader) {
30+
Quill.register('modules/imageUploader', ImageUploader);
31+
registered_plugins.image_uploader = true;
32+
}
33+
var opts = plugin_options.image_uploader;
34+
options.modules.imageUploader = setupImageUploader(opts.server_url, opts.field_name);
35+
}
36+
37+
// Init editor
2338
editors[i]['_quill-editor'] = new Quill(content, options);
2439
editors[i].classList += ' quill-editor--active';
2540
}
@@ -40,6 +55,33 @@ function initQuillEditors() {
4055
}
4156
}
4257

58+
function setupImageUploader(server_url, field_name) {
59+
return {
60+
upload: file => {
61+
return new Promise((resolve, reject) => {
62+
const formData = new FormData();
63+
formData.append(field_name || 'file_upload', file);
64+
65+
fetch(server_url, {
66+
body: formData,
67+
headers: {
68+
'X-CSRF-Token': document.querySelector('meta[name="csrf-token"]').getAttribute('content')
69+
},
70+
method: 'POST'
71+
}).then(response => response.json())
72+
.then(result => {
73+
resolve(result.url);
74+
})
75+
.catch(error => {
76+
reject('Upload failed');
77+
console.error('Error: ', error);
78+
});
79+
});
80+
}
81+
}
82+
}
83+
84+
// --- events ------------------------------------------------------------------
4385
$(document).ready( function() {
4486
initQuillEditors();
4587
});
Lines changed: 33 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,33 @@
1+
.image-uploading {
2+
position: relative;
3+
display: inline-block;
4+
}
5+
6+
.image-uploading img {
7+
max-width: 98% !important;
8+
filter: blur(5px);
9+
opacity: 0.3;
10+
}
11+
12+
.image-uploading::before {
13+
content: "";
14+
box-sizing: border-box;
15+
position: absolute;
16+
top: 50%;
17+
left: 50%;
18+
width: 30px;
19+
height: 30px;
20+
margin-top: -15px;
21+
margin-left: -15px;
22+
border-radius: 50%;
23+
border: 3px solid #ccc;
24+
border-top-color: #1e986c;
25+
z-index: 1;
26+
animation: spinner 0.6s linear infinite;
27+
}
28+
29+
@keyframes spinner {
30+
to {
31+
transform: rotate(360deg);
32+
}
33+
}

0 commit comments

Comments
 (0)