mirror of
https://github.com/ae-utbm/sith.git
synced 2025-03-09 23:07:11 +00:00
Add image upload to easymde widget
This commit is contained in:
parent
6ec79966b1
commit
d65cabe4f3
@ -42,11 +42,11 @@ class MarkdownController(ControllerBase):
|
|||||||
|
|
||||||
@api_controller("/upload")
|
@api_controller("/upload")
|
||||||
class UploadController(ControllerBase):
|
class UploadController(ControllerBase):
|
||||||
@route.post("/images", response=UploadedFileSchema, permissions=[IsOldSubscriber])
|
@route.post("/image", response=UploadedFileSchema, permissions=[IsOldSubscriber])
|
||||||
def upload_assets(self, file: UploadedFile):
|
def upload_image(self, file: UploadedFile):
|
||||||
if file.content_type.split("/")[0] != "image":
|
if file.content_type.split("/")[0] != "image":
|
||||||
return self.create_response(
|
return self.create_response(
|
||||||
message=f"{file.name} isn't a file image", status_code=400
|
message=f"{file.name} isn't a file image", status_code=415
|
||||||
)
|
)
|
||||||
|
|
||||||
def convert_image(file: UploadedFile) -> ContentFile:
|
def convert_image(file: UploadedFile) -> ContentFile:
|
||||||
@ -60,7 +60,7 @@ class UploadController(ControllerBase):
|
|||||||
converted = convert_image(file)
|
converted = convert_image(file)
|
||||||
except UnidentifiedImageError:
|
except UnidentifiedImageError:
|
||||||
return self.create_response(
|
return self.create_response(
|
||||||
message=f"{file.name} can't be processed", status_code=400
|
message=f"{file.name} can't be processed", status_code=415
|
||||||
)
|
)
|
||||||
|
|
||||||
with transaction.atomic():
|
with transaction.atomic():
|
||||||
|
@ -6,13 +6,43 @@ import { inheritHtmlElement, registerComponent } from "#core:utils/web-component
|
|||||||
import type CodeMirror from "codemirror";
|
import type CodeMirror from "codemirror";
|
||||||
// biome-ignore lint/style/useNamingConvention: This is how they called their namespace
|
// biome-ignore lint/style/useNamingConvention: This is how they called their namespace
|
||||||
import EasyMDE from "easymde";
|
import EasyMDE from "easymde";
|
||||||
import { markdownRenderMarkdown } from "#openapi";
|
import { markdownRenderMarkdown, uploadUploadImage } from "#openapi";
|
||||||
|
|
||||||
const loadEasyMde = (textarea: HTMLTextAreaElement) => {
|
const loadEasyMde = (textarea: HTMLTextAreaElement) => {
|
||||||
new EasyMDE({
|
const easymde = new EasyMDE({
|
||||||
element: textarea,
|
element: textarea,
|
||||||
spellChecker: false,
|
spellChecker: false,
|
||||||
autoDownloadFontAwesome: false,
|
autoDownloadFontAwesome: false,
|
||||||
|
uploadImage: true,
|
||||||
|
imagePathAbsolute: false,
|
||||||
|
imageUploadFunction: async (file, onSuccess, onError) => {
|
||||||
|
const response = await uploadUploadImage({
|
||||||
|
body: {
|
||||||
|
file: file,
|
||||||
|
},
|
||||||
|
});
|
||||||
|
if (response.response.status !== 200) {
|
||||||
|
onError(gettext("Invalid file"));
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
onSuccess(response.data.href);
|
||||||
|
// Workaround function to add ! and image name to uploaded image
|
||||||
|
// Without this, you get [](url) instead of 
|
||||||
|
let cursor = easymde.codemirror.getCursor();
|
||||||
|
easymde.codemirror.setSelection({ line: cursor.line, ch: cursor.ch - 1 });
|
||||||
|
easymde.codemirror.replaceSelection("!");
|
||||||
|
|
||||||
|
easymde.codemirror.setSelection({ line: cursor.line, ch: cursor.ch + 1 });
|
||||||
|
easymde.codemirror.replaceSelection(file.name.split(".").slice(0, -1).join("."));
|
||||||
|
|
||||||
|
// Move cursor at the end of the url and add a new line
|
||||||
|
cursor = easymde.codemirror.getCursor();
|
||||||
|
easymde.codemirror.setSelection({
|
||||||
|
line: cursor.line,
|
||||||
|
ch: cursor.ch + response.data.href.length + 3,
|
||||||
|
});
|
||||||
|
easymde.codemirror.replaceSelection("\n");
|
||||||
|
},
|
||||||
previewRender: (plainText: string, preview: MarkdownInput) => {
|
previewRender: (plainText: string, preview: MarkdownInput) => {
|
||||||
/* This is wrapped this way to allow time for Alpine to be loaded on the page */
|
/* This is wrapped this way to allow time for Alpine to be loaded on the page */
|
||||||
return Alpine.debounce((plainText: string, preview: MarkdownInput) => {
|
return Alpine.debounce((plainText: string, preview: MarkdownInput) => {
|
||||||
@ -30,6 +60,14 @@ const loadEasyMde = (textarea: HTMLTextAreaElement) => {
|
|||||||
}, 300)(plainText, preview);
|
}, 300)(plainText, preview);
|
||||||
},
|
},
|
||||||
forceSync: true, // Avoid validation error on generic create view
|
forceSync: true, // Avoid validation error on generic create view
|
||||||
|
imageTexts: {
|
||||||
|
sbInit: gettext("Attach files by drag and dropping or pasting from clipboard."),
|
||||||
|
sbOnDragEnter: gettext("Drop image to upload it."),
|
||||||
|
sbOnDrop: gettext("Uploading image #images_names# …"),
|
||||||
|
sbProgress: gettext("Uploading #file_name#: #progress#%"),
|
||||||
|
sbOnUploaded: gettext("Uploaded #image_name#"),
|
||||||
|
sizeUnits: gettext(" B, KB, MB"),
|
||||||
|
},
|
||||||
toolbar: [
|
toolbar: [
|
||||||
{
|
{
|
||||||
name: "heading-smaller",
|
name: "heading-smaller",
|
||||||
@ -120,6 +158,12 @@ const loadEasyMde = (textarea: HTMLTextAreaElement) => {
|
|||||||
className: "fa-regular fa-image",
|
className: "fa-regular fa-image",
|
||||||
title: gettext("Insert image"),
|
title: gettext("Insert image"),
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
name: "upload-image",
|
||||||
|
action: EasyMDE.drawUploadedImage,
|
||||||
|
className: "fa-solid fa-file-arrow-up",
|
||||||
|
title: gettext("Upload image"),
|
||||||
|
},
|
||||||
{
|
{
|
||||||
name: "table",
|
name: "table",
|
||||||
action: EasyMDE.drawTable,
|
action: EasyMDE.drawTable,
|
||||||
|
@ -7,7 +7,7 @@
|
|||||||
msgid ""
|
msgid ""
|
||||||
msgstr ""
|
msgstr ""
|
||||||
"Report-Msgid-Bugs-To: \n"
|
"Report-Msgid-Bugs-To: \n"
|
||||||
"POT-Creation-Date: 2025-02-25 16:10+0100\n"
|
"POT-Creation-Date: 2025-02-27 00:27+0100\n"
|
||||||
"PO-Revision-Date: 2024-09-17 11:54+0200\n"
|
"PO-Revision-Date: 2024-09-17 11:54+0200\n"
|
||||||
"Last-Translator: Sli <antoine@bartuccio.fr>\n"
|
"Last-Translator: Sli <antoine@bartuccio.fr>\n"
|
||||||
"Language-Team: AE info <ae.info@utbm.fr>\n"
|
"Language-Team: AE info <ae.info@utbm.fr>\n"
|
||||||
@ -34,6 +34,7 @@ msgid "Delete"
|
|||||||
msgstr "Supprimer"
|
msgstr "Supprimer"
|
||||||
|
|
||||||
#: com/static/bundled/com/components/moderation-alert-index.ts
|
#: com/static/bundled/com/components/moderation-alert-index.ts
|
||||||
|
#, javascript-format
|
||||||
msgid ""
|
msgid ""
|
||||||
"This event will take place every week for %s weeks. If you publish or delete "
|
"This event will take place every week for %s weeks. If you publish or delete "
|
||||||
"this event, it will also be published (or deleted) for the following weeks."
|
"this event, it will also be published (or deleted) for the following weeks."
|
||||||
@ -54,6 +55,34 @@ msgstr "Vous devez taper %(number)s caractères de plus"
|
|||||||
msgid "No results found"
|
msgid "No results found"
|
||||||
msgstr "Aucun résultat trouvé"
|
msgstr "Aucun résultat trouvé"
|
||||||
|
|
||||||
|
#: core/static/bundled/core/components/easymde-index.ts
|
||||||
|
msgid "Invalid file"
|
||||||
|
msgstr "Fichier invalide"
|
||||||
|
|
||||||
|
#: core/static/bundled/core/components/easymde-index.ts
|
||||||
|
msgid "Attach files by drag and dropping or pasting from clipboard."
|
||||||
|
msgstr "Ajoutez des fichiez en glissant déposant ou collant depuis votre presse papier."
|
||||||
|
|
||||||
|
#: core/static/bundled/core/components/easymde-index.ts
|
||||||
|
msgid "Drop image to upload it."
|
||||||
|
msgstr "Glissez une image pour la téléverser."
|
||||||
|
|
||||||
|
#: core/static/bundled/core/components/easymde-index.ts
|
||||||
|
msgid "Uploading image #images_names# …"
|
||||||
|
msgstr "Téléversement de l'image #images_names# …"
|
||||||
|
|
||||||
|
#: core/static/bundled/core/components/easymde-index.ts
|
||||||
|
msgid "Uploading #file_name#: #progress#%"
|
||||||
|
msgstr "Téléversement de #file_name#: #progress#%"
|
||||||
|
|
||||||
|
#: core/static/bundled/core/components/easymde-index.ts
|
||||||
|
msgid "Uploaded #image_name#"
|
||||||
|
msgstr "#image_name# téléversé"
|
||||||
|
|
||||||
|
#: core/static/bundled/core/components/easymde-index.ts
|
||||||
|
msgid " B, KB, MB"
|
||||||
|
msgstr " B, KB, MB"
|
||||||
|
|
||||||
#: core/static/bundled/core/components/easymde-index.ts
|
#: core/static/bundled/core/components/easymde-index.ts
|
||||||
msgid "Heading"
|
msgid "Heading"
|
||||||
msgstr "Titre"
|
msgstr "Titre"
|
||||||
@ -106,6 +135,10 @@ msgstr "Insérer lien"
|
|||||||
msgid "Insert image"
|
msgid "Insert image"
|
||||||
msgstr "Insérer image"
|
msgstr "Insérer image"
|
||||||
|
|
||||||
|
#: core/static/bundled/core/components/easymde-index.ts
|
||||||
|
msgid "Upload image"
|
||||||
|
msgstr "Téléverser une image"
|
||||||
|
|
||||||
#: core/static/bundled/core/components/easymde-index.ts
|
#: core/static/bundled/core/components/easymde-index.ts
|
||||||
msgid "Insert table"
|
msgid "Insert table"
|
||||||
msgstr "Insérer tableau"
|
msgstr "Insérer tableau"
|
||||||
|
12
package-lock.json
generated
12
package-lock.json
generated
@ -26,7 +26,7 @@
|
|||||||
"cytoscape-cxtmenu": "^3.5.0",
|
"cytoscape-cxtmenu": "^3.5.0",
|
||||||
"cytoscape-klay": "^3.1.4",
|
"cytoscape-klay": "^3.1.4",
|
||||||
"d3-force-3d": "^3.0.5",
|
"d3-force-3d": "^3.0.5",
|
||||||
"easymde": "^2.18.0",
|
"easymde": "^2.19.0",
|
||||||
"glob": "^11.0.0",
|
"glob": "^11.0.0",
|
||||||
"htmx.org": "^2.0.3",
|
"htmx.org": "^2.0.3",
|
||||||
"jquery": "^3.7.1",
|
"jquery": "^3.7.1",
|
||||||
@ -3655,14 +3655,14 @@
|
|||||||
"license": "MIT"
|
"license": "MIT"
|
||||||
},
|
},
|
||||||
"node_modules/easymde": {
|
"node_modules/easymde": {
|
||||||
"version": "2.18.0",
|
"version": "2.19.0",
|
||||||
"resolved": "https://registry.npmjs.org/easymde/-/easymde-2.18.0.tgz",
|
"resolved": "https://registry.npmjs.org/easymde/-/easymde-2.19.0.tgz",
|
||||||
"integrity": "sha512-IxVVUxNWIoXLeqtBU4BLc+eS/ScYhT1Dcb6yF5Wchoj1iXAV+TIIDWx+NCaZhY7RcSHqDPKllbYq7nwGKILnoA==",
|
"integrity": "sha512-4F1aNImqse+9xIjLh9ttfpOVenecjFPxUmKbl1tGp72Z+OyIqLZPE/SgNyy88c/xU0mOy0WC3+tfbZDQ5PDWhg==",
|
||||||
"license": "MIT",
|
"license": "MIT",
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"@types/codemirror": "^5.60.4",
|
"@types/codemirror": "^5.60.10",
|
||||||
"@types/marked": "^4.0.7",
|
"@types/marked": "^4.0.7",
|
||||||
"codemirror": "^5.63.1",
|
"codemirror": "^5.65.15",
|
||||||
"codemirror-spell-checker": "1.1.2",
|
"codemirror-spell-checker": "1.1.2",
|
||||||
"marked": "^4.1.0"
|
"marked": "^4.1.0"
|
||||||
}
|
}
|
||||||
|
@ -52,7 +52,7 @@
|
|||||||
"cytoscape-cxtmenu": "^3.5.0",
|
"cytoscape-cxtmenu": "^3.5.0",
|
||||||
"cytoscape-klay": "^3.1.4",
|
"cytoscape-klay": "^3.1.4",
|
||||||
"d3-force-3d": "^3.0.5",
|
"d3-force-3d": "^3.0.5",
|
||||||
"easymde": "^2.18.0",
|
"easymde": "^2.19.0",
|
||||||
"glob": "^11.0.0",
|
"glob": "^11.0.0",
|
||||||
"htmx.org": "^2.0.3",
|
"htmx.org": "^2.0.3",
|
||||||
"jquery": "^3.7.1",
|
"jquery": "^3.7.1",
|
||||||
|
Loading…
x
Reference in New Issue
Block a user