Move easymde widget to easymde-index.js

This commit is contained in:
Antoine Bartuccio 2024-10-02 22:06:55 +02:00 committed by Bartuccio Antoine
parent cacdf600f4
commit e5aa7aa866
5 changed files with 639 additions and 668 deletions

View File

@ -2,4 +2,188 @@ import "codemirror/lib/codemirror.css";
import "easymde/src/css/easymde.css";
import EasyMDE from "easymde";
window.EasyMDE = EasyMDE;
// This scripts dependens on Alpine but it should be loaded on every page
/**
* Create a new easymde based textarea
* @param {HTMLTextAreaElement} textarea to use
* @param {string} link to the markdown api
**/
function easymde_factory (textarea, markdown_api_url) {
const easymde = new EasyMDE({
element: textarea,
spellChecker: false,
autoDownloadFontAwesome: false,
previewRender: Alpine.debounce(async (plainText, preview) => {
const res = await fetch(markdown_api_url, {
method: "POST",
body: JSON.stringify({ text: plainText }),
});
preview.innerHTML = await res.text();
return null;
}, 300),
forceSync: true, // Avoid validation error on generic create view
toolbar: [
{
name: "heading-smaller",
action: EasyMDE.toggleHeadingSmaller,
className: "fa fa-header",
title: gettext("Heading"),
},
{
name: "italic",
action: EasyMDE.toggleItalic,
className: "fa fa-italic",
title: gettext("Italic"),
},
{
name: "bold",
action: EasyMDE.toggleBold,
className: "fa fa-bold",
title: gettext("Bold"),
},
{
name: "strikethrough",
action: EasyMDE.toggleStrikethrough,
className: "fa fa-strikethrough",
title: gettext("Strikethrough"),
},
{
name: "underline",
action: function customFunction(editor) {
let cm = editor.codemirror;
cm.replaceSelection("__" + cm.getSelection() + "__");
},
className: "fa fa-underline",
title: gettext("Underline"),
},
{
name: "superscript",
action: function customFunction(editor) {
let cm = editor.codemirror;
cm.replaceSelection("^" + cm.getSelection() + "^");
},
className: "fa fa-superscript",
title: gettext("Superscript"),
},
{
name: "subscript",
action: function customFunction(editor) {
let cm = editor.codemirror;
cm.replaceSelection("~" + cm.getSelection() + "~");
},
className: "fa fa-subscript",
title: gettext("Subscript"),
},
{
name: "code",
action: EasyMDE.toggleCodeBlock,
className: "fa fa-code",
title: gettext("Code"),
},
"|",
{
name: "quote",
action: EasyMDE.toggleBlockquote,
className: "fa fa-quote-left",
title: gettext("Quote"),
},
{
name: "unordered-list",
action: EasyMDE.toggleUnorderedList,
className: "fa fa-list-ul",
title: gettext("Unordered list"),
},
{
name: "ordered-list",
action: EasyMDE.toggleOrderedList,
className: "fa fa-list-ol",
title: gettext("Ordered list"),
},
"|",
{
name: "link",
action: EasyMDE.drawLink,
className: "fa fa-link",
title: gettext("Insert link"),
},
{
name: "image",
action: EasyMDE.drawImage,
className: "fa-regular fa-image",
title: gettext("Insert image"),
},
{
name: "table",
action: EasyMDE.drawTable,
className: "fa fa-table",
title: gettext("Insert table"),
},
"|",
{
name: "clean-block",
action: EasyMDE.cleanBlock,
className: "fa fa-eraser fa-clean-block",
title: gettext("Clean block"),
},
"|",
{
name: "preview",
action: EasyMDE.togglePreview,
className: "fa fa-eye no-disable",
title: gettext("Toggle preview"),
},
{
name: "side-by-side",
action: EasyMDE.toggleSideBySide,
className: "fa fa-columns no-disable no-mobile",
title: gettext("Toggle side by side"),
},
{
name: "fullscreen",
action: EasyMDE.toggleFullScreen,
className: "fa fa-arrows-alt no-disable no-mobile",
title: gettext("Toggle fullscreen"),
},
"|",
{
name: "guide",
action: "/page/Aide_sur_la_syntaxe",
className: "fa fa-question-circle",
title: gettext("Markdown guide"),
},
],
});
const submits = textarea
.closest("form")
.querySelectorAll('input[type="submit"]');
const parentDiv = textarea.parentElement;
let submitPressed = false;
function checkMarkdownInput(e) {
// an attribute is null if it does not exist, else a string
const required = textarea.getAttribute("required") != null;
const length = textarea.value.trim().length;
if (required && length == 0) {
parentDiv.style.boxShadow = "red 0px 0px 1.5px 1px";
} else {
parentDiv.style.boxShadow = "";
}
}
function onSubmitClick(e) {
if (!submitPressed) {
easymde.codemirror.on("change", checkMarkdownInput);
}
submitPressed = true;
checkMarkdownInput(e);
}
submits.forEach((submit) => {
submit.addEventListener("click", onSubmitClick);
});
};
window.easymde_factory = easymde_factory;

View File

@ -1,198 +1,15 @@
<div>
{# Depends on this package https://github.com/lonaru/easy-markdown-editor #}
<textarea name="{{ widget.name }}"{% include "django/forms/widgets/attrs.html" %}>{% if widget.value %}{{ widget.value }}{% endif %}</textarea>
{# The easymde script can be included twice, it's safe in the code #}
<script src="{{ statics.js }}"> </script>
<script src="{{ statics.js }}" defer> </script>
<link rel="stylesheet" type="text/css" href="{{ statics.css }}" defer>
<script type="text/javascript">
$(function() {
const css = "{{ statics.css }}";
let lastAPICall;
// Only import the css once
if (!document.head.innerHTML.includes(css)) {
document.head.innerHTML += '<link rel="stylesheet" href="' + css + '">';
}
// Pretty markdown input
const easymde = new EasyMDE({
element: document.getElementById("{{ widget.attrs.id }}"),
spellChecker: false,
autoDownloadFontAwesome: false,
previewRender: function (plainText, preview) {
clearTimeout(lastAPICall);
lastAPICall = setTimeout(async () => {
const res = await fetch("{{ markdown_api_url }}", {
method: "POST",
body: JSON.stringify({ text: plainText }),
});
preview.innerHTML = await res.text();
}, 300);
return null;
},
forceSync: true, // Avoid validation error on generic create view
toolbar: [
{
name: "heading-smaller",
action: EasyMDE.toggleHeadingSmaller,
className: "fa fa-header",
title: "{{ translations.heading_smaller }}"
},
{
name: "italic",
action: EasyMDE.toggleItalic,
className: "fa fa-italic",
title: "{{ translations.italic }}"
},
{
name: "bold",
action: EasyMDE.toggleBold,
className: "fa fa-bold",
title: "{{ translations.bold }}"
},
{
name: "strikethrough",
action: EasyMDE.toggleStrikethrough,
className: "fa fa-strikethrough",
title: "{{ translations.strikethrough }}"
},
{
name: "underline",
action: function customFunction(editor){
let cm = editor.codemirror;
cm.replaceSelection('__' + cm.getSelection() + '__');
},
className: "fa fa-underline",
title: "{{ translations.underline }}"
},
{
name: "superscript",
action: function customFunction(editor){
let cm = editor.codemirror;
cm.replaceSelection('^' + cm.getSelection() + '^');
},
className: "fa fa-superscript",
title: "{{ translations.superscript }}"
},
{
name: "subscript",
action: function customFunction(editor){
let cm = editor.codemirror;
cm.replaceSelection('~' + cm.getSelection() + '~');
},
className: "fa fa-subscript",
title: "{{ translations.subscript }}"
},
{
name: "code",
action: EasyMDE.toggleCodeBlock,
className: "fa fa-code",
title: "{{ translations.code }}"
},
"|",
{
name: "quote",
action: EasyMDE.toggleBlockquote,
className: "fa fa-quote-left",
title: "{{ translations.quote }}"
},
{
name: "unordered-list",
action: EasyMDE.toggleUnorderedList,
className: "fa fa-list-ul",
title: "{{ translations.unordered_list }}"
},
{
name: "ordered-list",
action: EasyMDE.toggleOrderedList,
className: "fa fa-list-ol",
title: "{{ translations.ordered_list }}"
},
"|",
{
name: "link",
action: EasyMDE.drawLink,
className: "fa fa-link",
title: "{{ translations.link }}"
},
{
name: "image",
action: EasyMDE.drawImage,
className: "fa-regular fa-image",
title: "{{ translations.image }}"
},
{
name: "table",
action: EasyMDE.drawTable,
className: "fa fa-table",
title: "{{ translations.table }}"
},
"|",
{
name: "clean-block",
action: EasyMDE.cleanBlock,
className: "fa fa-eraser fa-clean-block",
title: "{{ translations.clean_block }}"
},
"|",
{
name: "preview",
action: EasyMDE.togglePreview,
className: "fa fa-eye no-disable",
title: "{{ translations.preview }}"
},
{
name: "side-by-side",
action: EasyMDE.toggleSideBySide,
className: "fa fa-columns no-disable no-mobile",
title: "{{ translations.side_by_side }}"
},
{
name: "fullscreen",
action: EasyMDE.toggleFullScreen,
className: "fa fa-arrows-alt no-disable no-mobile",
title: "{{ translations.fullscreen }}"
},
"|",
{
name: "guide",
action: "/page/Aide_sur_la_syntaxe",
className: "fa fa-question-circle",
title: "{{ translations.guide }}"
},
]
});
const textarea = document.getElementById('{{ widget.attrs.id }}');
const submits = textarea
.closest('form')
.querySelectorAll('input[type="submit"]');
const parentDiv = textarea.parentElement;
let submitPressed = false;
function checkMarkdownInput(e) {
// an attribute is null if it does not exist, else a string
const required = textarea.getAttribute('required') != null;
const length = textarea.value.trim().length;
if (required && length == 0) {
parentDiv.style.boxShadow = 'red 0px 0px 1.5px 1px';
} else {
parentDiv.style.boxShadow = '';
}
}
function onSubmitClick(e) {
if (!submitPressed) {
easymde.codemirror.on('change', checkMarkdownInput);
}
submitPressed = true;
checkMarkdownInput(e);
}
submits.forEach((submit) => {
submit.addEventListener('click', onSubmitClick);
})
addEventListener("DOMContentLoaded", (event) => {
easymde_factory(
document.getElementById("{{ widget.attrs.id }}"),
"{{ markdown_api_url }}",
);
})
</script>
</div>

View File

@ -76,27 +76,6 @@ class MarkdownInput(Textarea):
"js": static("webpack/easymde-index.js"),
"css": static("webpack/easymde-index.css"),
}
context["translations"] = {
"heading_smaller": _("Heading"),
"italic": _("Italic"),
"bold": _("Bold"),
"strikethrough": _("Strikethrough"),
"underline": _("Underline"),
"superscript": _("Superscript"),
"subscript": _("Subscript"),
"code": _("Code"),
"quote": _("Quote"),
"unordered_list": _("Unordered list"),
"ordered_list": _("Ordered list"),
"image": _("Insert image"),
"link": _("Insert link"),
"table": _("Insert table"),
"clean_block": _("Clean block"),
"preview": _("Toggle preview"),
"side_by_side": _("Toggle side by side"),
"fullscreen": _("Toggle fullscreen"),
"guide": _("Markdown guide"),
}
context["markdown_api_url"] = reverse("api:markdown")
return context

File diff suppressed because it is too large Load Diff

View File

@ -7,7 +7,7 @@
msgid ""
msgstr ""
"Report-Msgid-Bugs-To: \n"
"POT-Creation-Date: 2024-09-27 22:32+0200\n"
"POT-Creation-Date: 2024-10-02 17:47+0200\n"
"PO-Revision-Date: 2024-09-17 11:54+0200\n"
"Last-Translator: Sli <antoine@bartuccio.fr>\n"
"Language-Team: AE info <ae.info@utbm.fr>\n"
@ -26,14 +26,90 @@ msgstr "arbre_genealogique.%(extension)s"
msgid "captured.%s"
msgstr "capture.%s"
#: core/static/webpack/easymde-index.js:27
msgid "Heading"
msgstr "Titre"
#: core/static/webpack/easymde-index.js:33
msgid "Italic"
msgstr "Italique"
#: core/static/webpack/easymde-index.js:39
msgid "Bold"
msgstr "Gras"
#: core/static/webpack/easymde-index.js:45
msgid "Strikethrough"
msgstr "Barré"
#: core/static/webpack/easymde-index.js:54
msgid "Underline"
msgstr "Souligné"
#: core/static/webpack/easymde-index.js:63
msgid "Superscript"
msgstr "Exposant"
#: core/static/webpack/easymde-index.js:72
msgid "Subscript"
msgstr "Indice"
#: core/static/webpack/easymde-index.js:78
msgid "Code"
msgstr "Code"
#: core/static/webpack/easymde-index.js:85
msgid "Quote"
msgstr "Citation"
#: core/static/webpack/easymde-index.js:91
msgid "Unordered list"
msgstr "Liste non ordonnée"
#: core/static/webpack/easymde-index.js:97
msgid "Ordered list"
msgstr "Liste ordonnée"
#: core/static/webpack/easymde-index.js:104
msgid "Insert link"
msgstr "Insérer lien"
#: core/static/webpack/easymde-index.js:110
msgid "Insert image"
msgstr "Insérer image"
#: core/static/webpack/easymde-index.js:116
msgid "Insert table"
msgstr "Insérer tableau"
#: core/static/webpack/easymde-index.js:123
msgid "Clean block"
msgstr "Nettoyer bloc"
#: core/static/webpack/easymde-index.js:130
msgid "Toggle preview"
msgstr "Activer la prévisualisation"
#: core/static/webpack/easymde-index.js:136
msgid "Toggle side by side"
msgstr "Activer la vue côte à côte"
#: core/static/webpack/easymde-index.js:142
msgid "Toggle fullscreen"
msgstr "Activer le plein écran"
#: core/static/webpack/easymde-index.js:149
msgid "Markdown guide"
msgstr "Guide markdown"
#: eboutic/static/eboutic/js/makecommand.js:50
msgid "Incorrect value"
msgstr "Valeur incorrecte"
#: sas/static/sas/js/viewer.js:196
#: sas/static/sas/js/viewer.js:201
msgid "Couldn't moderate picture"
msgstr "Echec de la suppression de la photo"
msgstr "Il n'a pas été possible de modérer l'image"
#: sas/static/sas/js/viewer.js:209
#: sas/static/sas/js/viewer.js:214
msgid "Couldn't delete picture"
msgstr "Echec de la suppression de la photo"
msgstr "Il n'a pas été possible de supprimer l'image"