Adding Trix editor to Phoenix liveview
I was looking for a simple rich text editor to add to a liveview application. A quick look about and you will see that there are many out there. A lot offer many features and are very configurable. And here lies the issue, I don't want to spend hours learning about an editor, that once added, hopefully, I don't go near often.
After some pondering, I decided that Trix would give the right amount of features with a simple way to include the editor onto a liveview page.
Adding Trix
To add Trix to the project you will need to add the javascript and CSS files as described on the Trix Github page.
Adding Trix to the page was simple. Add a hidden input field that provides the data store for the editor and the editor element and you are off.
<%= hidden_input f, :information %>
<div id="information-editor" phx-update="ignore">
<trix-editor input="page_information">
</trix-editor>
</div>
<%= error_tag(f, :information) %>
In the snippet, you can see the editor is informed of the ID of the hidden field via the input
attribute. This needs to be the ID as generated by Phoenix if you use it to generate the hidden input.
By far the most important things is to remove the editor from liveviews update process. This is achieved using phx-update="ignore"
on the surrounding div
.
I also wanted to remove some of the buttons from toolbar. Trix unfortunately does not easily allow this. You could modify the source code or as in my case I just need to remove a few buttons, I could achieve it easily with some CSS
.trix-button--icon-strike { display: none; }
.trix-button--icon-quote { display: none; }
.trix-button--icon-code { display: none; }
.trix-button--icon-number-list { display: none; }
.trix-button--icon-decrease-nesting-level { display: none; }
.trix-button--icon-increase-nesting-level { display: none; }
.trix-button-group--file-tools { display: none !important; }
Updated 2020-10-07
Things change!
I now have the requirement that user can select pre-formatted text into the editor. Basically the user can set up a number of named text entries in their profile. Then when using the editor, they can select a named piece of text from a select box and have the text inserted into the editor.
This caused an issue, although the hidden field was updated, Trix was not.
Fortunately JS hooks came to the rescue. By adding a hook to detect the change in the hidden field value from the server, Trix can be told to replace its content.
<%= hidden_input f, :information, phx_hook: "TrixEditor" %>
<div id="information-editor" phx-update="ignore">
<trix-editor input="page_information">
</trix-editor>
</div>
<%= error_tag(f, :information) %>
And adding the hook code
Hooks.TrixEditor = {
updated() {
var trixEditor = document.querySelector("trix-editor")
if (null != trixEditor) {
trixEditor.editor.loadHTML(this.el.value);
}
}
}
The editor is now updated with the content correctly.