Skip to content

Commit

Permalink
feat(frontend): add easy-markdown-editor
Browse files Browse the repository at this point in the history
  • Loading branch information
paulrobertlloyd committed Apr 5, 2024
1 parent d57face commit 0511cc7
Show file tree
Hide file tree
Showing 9 changed files with 416 additions and 34 deletions.
12 changes: 12 additions & 0 deletions helpers/frontend/views/frontend-form.njk
Original file line number Diff line number Diff line change
Expand Up @@ -65,6 +65,18 @@
hint: "Textarea hint text"
}) }}

{{ textarea({
errorMessage: { text: "Richtext input error" } if errors,
name: "richtext",
label: "Richtext",
hint: "Richtext hint text",
field: {
attributes: {
editor: true
}
}
}) }}

{{ textarea({
errorMessage: { text: "Readonly textarea input error" } if errors,
name: "textarea-readonly",
Expand Down
63 changes: 63 additions & 0 deletions package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

63 changes: 47 additions & 16 deletions packages/frontend/components/textarea/index.js
Original file line number Diff line number Diff line change
@@ -1,31 +1,62 @@
import { debounce } from "../../lib/utils/debounce.js";
import EasyMDE from "easymde";

export const TextareaFieldComponent = class extends HTMLElement {
constructor() {
super();

this.adjustHeight = this.adjustHeight.bind(this);
this.editor = this.getAttribute("editor");
this.editorId = this.getAttribute("editor-id");
this.$textarea = this.querySelector("textarea");
}

connectedCallback() {
const delay = 100;
if (this.editor !== "") {
return;
}

this.$textarea.style.overflow = "hidden";
this.onResize =
delay > 0 ? debounce(this.adjustHeight, delay) : this.adjustHeight;
this.adjustHeight();

this.$textarea.addEventListener("input", this.adjustHeight);
window.addEventListener("resize", this.onResize);
new EasyMDE({
autosave: {
enabled: true,
uniqueId: this.editorId || this.$textarea.id,
},
blockStyles: {
bold: "**",
italic: "_",
},
element: this.$textarea,
hideIcons: ["guide", "image"],
// @ts-ignore
showIcons: ["code", "upload-image"],
imageUploadFunction: this.uploadFile,
previewClass: ["editor-preview", "s-flow"],
status: ["upload-image", "words", "autosave", "cursor"],
uploadImage: true,
unorderedListStyle: "-",
});
}

disconnectedCallback() {
window.removeEventListener("resize", this.onResize);
}
/**
* Upload file
* @param {object} file - File
* @param {Function} onSuccess - Success callback
* @param {Function} onError - Error callback
* @returns {Promise<string>} - File URL or error message
*/
async uploadFile(file, onSuccess, onError) {
const formData = new FormData();
formData.append("file", file);

try {
const endpointResponse = await fetch("http://localhost:3000/media", {
method: "POST",
body: formData,
});

adjustHeight() {
this.$textarea.style.height = "auto";
this.$textarea.style.height = `${this.$textarea.scrollHeight + 4}px`;
return endpointResponse.ok
? onSuccess(endpointResponse.headers.get("location"))
: onError(endpointResponse.statusText);
} catch (error) {
onError(error.message);
}
}
};
1 change: 1 addition & 0 deletions packages/frontend/components/textarea/styles.css
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@ textarea-field {
border-color: var(--color-on-background);
border-width: var(--input-border-width-focus);
inset-block-start: calc(var(--input-border-width-focus-offset) * -1);
margin-block-end: calc(var(--input-border-width-focus-offset) * -2);
padding-inline-start: calc(
var(--space-s) - var(--input-border-width-focus-offset)
);
Expand Down
18 changes: 0 additions & 18 deletions packages/frontend/lib/utils/debounce.js

This file was deleted.

1 change: 1 addition & 0 deletions packages/frontend/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -41,6 +41,7 @@
"@rollup/plugin-commonjs": "^25.0.3",
"@rollup/plugin-node-resolve": "^15.0.0",
"color": "^4.0.1",
"easymde": "^2.18.0",
"iso-639-1": "^3.0.0",
"lightningcss": "^1.22.0",
"lodash": "^4.17.21",
Expand Down
2 changes: 2 additions & 0 deletions packages/frontend/styles/app.css
Original file line number Diff line number Diff line change
Expand Up @@ -65,4 +65,6 @@
@import url("./utilities/visually-hidden.css");

/* Vendor */
@import url("./vendor/codemirror.css");
@import url("./vendor/easy-markdown-editor.css");
@import url("./vendor/markdown-it-prism.css");
49 changes: 49 additions & 0 deletions packages/frontend/styles/vendor/codemirror.css
Original file line number Diff line number Diff line change
@@ -0,0 +1,49 @@
@import url("../../../../node_modules/codemirror/lib/codemirror.css");

.CodeMirror {
--fieldset-flow-space: 0;

background: var(--color-background);
block-size: 60vh;
border: var(--input-border-width) solid transparent;
border-radius: var(--border-radius-small);
color: var(--color-on-backround);
font-family: var(--font-family-monospace);
margin-block-start: 0;
min-block-size: 30rem;
padding: var(--space-s);

& :focus-visible {
box-shadow: none;
}
}

.CodeMirror-focused:not(.CodeMirror-fullscreen) {
border-color: var(--color-on-background);
border-width: var(--input-border-width-focus);
margin-inline: calc(var(--input-border-width-focus) * -1);
outline: var(--input-border-width-focus) solid var(--color-focus);
padding-block: calc(var(--space-s) - var(--input-border-width-focus-offset));
padding-inline: calc(var(--space-s) + var(--input-border-width-focus-offset));
}

.CodeMirror-fullscreen {
block-size: auto;
inset: 0;
inset-block-start: 50px;
position: fixed;
z-index: 8;
}

.CodeMirror-placeholder {
color: var(--color-on-background);
opacity: 0.5;
}

.CodeMirror-selected {
background: var(--color-selection);
}

.CodeMirror-sided {
inline-size: 50%;
}
Loading

0 comments on commit 0511cc7

Please sign in to comment.