import { Components } from "gd-bs"; import Quill from "quill"; import * as Toolbars from "./toolbar"; import { IRichTextBox, IRichTextBoxProps, IFormControlPropsRichTextBox } from "./types"; /** * Toolbar Types */ export enum RichTextBoxTypes { None = 0, Basic = 1, Full = 2 } /** * Rich TextBox */ export const RichTextBox = (props: IRichTextBoxProps): IRichTextBox => { // Create the editor element let elRichTextBox = document.createElement("div"); elRichTextBox.classList.add("rich-textbox"); // Create the toolbar element let elToolbar = document.createElement("div"); elToolbar.classList.add("toolbar-container"); props.disabled ? null : elToolbar.classList.add("form-control"); elRichTextBox.appendChild(elToolbar); // Create the editor element let elEditor = document.createElement("div"); elEditor.classList.add("editor-container"); props.disabled ? elEditor.classList.add("rounded") : elEditor.classList.add("form-control"); elRichTextBox.appendChild(elEditor); // Get the options and default the values let options = props.options || {}; options.modules = options.modules || {}; options.placeholder ? options.placeholder = props.placeholder : null; options.readOnly == null && typeof (props.disabled) === "boolean" ? options.readOnly = props.disabled : null; options.theme = options.theme == null ? "snow" : options.theme; // See if are setting the default toolbar options let showToolbar = true; if (options.modules.toolbar == null) { // Set the toolbar options switch (props.toolbarType) { // None case RichTextBoxTypes.None: elToolbar.innerHTML = ""; showToolbar = false; break; // Basic case RichTextBoxTypes.Basic: elToolbar.innerHTML = Toolbars.BasicToolbar; break; // Default - Full default: elToolbar.innerHTML = Toolbars.FullToolbar; break; } // Set the toolbar options.modules.toolbar = elToolbar; } else { // Set the toolbar container options.modules.toolbar.container = elToolbar; } // Create the element let el = document.createElement("div"); el.appendChild(elRichTextBox); // See if we are rendering it to an element if (props.el) { // Ensure the parent element exists if (props.el.parentElement && props.el.parentElement.classList) { // Set the bootstrap class props.el.parentElement.classList.contains("bs") ? null : props.el.parentElement.classList.add("bs"); } // Append the elements while (el.children.length > 0) { props.el.appendChild(el.children[0]); } // Update the element el = props.el as any; } else { // Set the bootstrap class el.classList.add("bs"); } // Apply the plugin let quillObj = new Quill(elEditor, options as any); // See if we are hiding the toolbar if (!showToolbar) { // Remove the snow class elToolbar.classList.remove("ql-snow"); } // Create the object let obj = { el: elRichTextBox, elContents: quillObj.root, quillObj, getHtml: () => { return obj.getText() ? quillObj.root.innerHTML : ""; }, getText: () => { return quillObj.getText().trim(); }, setHtml: (value: string) => { // Convert the html to allow the library to run any conversions to display it correctly quillObj.setContents(quillObj.clipboard.convert({ html: value || "" })); } }; // Set the value props.value ? obj.setHtml(props.value) : null; // Execute the assign to event props.assignTo ? props.assignTo(obj) : null; // Return the object return obj; } // Customize the form control export const RichTextBoxControlType = 102; Components.FormControlTypes["RichTextBox"] = RichTextBoxControlType; Components.CustomControls.registerType(RichTextBoxControlType, (props: IFormControlPropsRichTextBox) => { let rtb: IRichTextBox = null; // Set the created method let onRendered = props.onControlRendered; props.onControlRendered = ctrl => { // Render a date/time rtb = RichTextBox({ className: props.className, disabled: props.isDisabled || props.isReadonly, el: ctrl.el, options: props.options, rows: props.rows, toolbarType: props.toolbarType, placeholder: props.placeholder, value: props.value }); // See if the label exists let elLabel: HTMLElement = ctrl["_elLabel"]; if (elLabel) { // Set the id and aria properties elLabel ? elLabel.id = (props.id || props.name) + "_label" : null; //rtb.el.querySelector("input").setAttribute("aria-labelledby", elLabel.id); } // Set the control ctrl.setControl(rtb); // Call the custom render event onRendered ? onRendered(ctrl) : null; } // Register a people picker props.onGetValue = (ctrl) => { // Return the value return rtb ? rtb.getHtml() : ctrl.value; }; });