CityWebConsultants / Iris

Modular content management and web application framework built with Node.js and MongoDB
http://irisjs.org
Other
9 stars 7 forks source link

Add textarea widget chooser on clientside #267

Closed adam-clarey closed 7 years ago

adam-clarey commented 8 years ago

Textareas can take different types of input and can be filtered in different ways when being displayed. For example 'plain text' vs 'filtered html' vs 'full html'.

At the minute, the widget is fixed for the each text area, its also not overly clear how these are set.

Drupal does this fairly well.

screen shot 2016-05-17 at 09 22 55

[Editing entity]

screen shot 2016-05-17 at 11 08 15

[Field settings]

Although, they generally have plain text and WYSIWYG editor widgets. Their widget and 'text filter' are also tightly coupled, so multiple filters can be defined, and you have to assign a widget for each type.

I think we could make use of multiple widgets, in particular WYSIWYG, Ace, codemirror etc. So we might want to de-couple the filter from the widget. Eg, User chooses 'Full html' for the filter type and 'Ace' for the widget. Or maybe a better way can be thought of.

Text filters should be tied to permissions, for instance, only trusted user roles should be allowed to have 'full html' rendered.

adam-clarey commented 8 years ago

Requirements:

Create a new field widget 'multiwidget' or named something better.

iris.modules.forms.globals.registerWidget(function () {

  JSONForm.elementTypes['multiwidget'] = JSON.parse(JSON.stringify(JSONForm.elementTypes['textarea']));

  JSONForm.elementTypes['multiwidget'].template
    = '<textarea id="<%= id %>" name="<%= node.name %>" ' +
      'class="<%= fieldHtmlClass || cls.textualInputClass %>" ' +
      'style="<%= elt.height ? "height:" + elt.height + ";" : "" %>width:<%= elt.width || "100%" %>;"' +
      '<%= (node.disabled? " disabled" : "")%>' +
      '<%= (node.isReadOnly() ? " readonly=\'readonly\'" : "") %>' +
      '<%= (node.schemaElement && node.schemaElement.maxLength ? " maxlength=\'" + node.schemaElement.maxLength + "\'" : "") %>' +
      '<%= (node.required ? " required=\'required\'" : "") %>' +
      '<%= (node.placeholder? " placeholder=" + \'"\' + escape(node.placeholder) + \'"\' : "")%>' +
      '><%= value %></textarea>

    // New widget selector
    <label>Choose widget</label>
    <select><%= widgetoptions %></select>';

  JSONForm.elementTypes['multiwidget'].onInsert = function (evt, node) {

    //JS to swap the textarea widget with the users choice.

  });
});

Extra scripts etc may need to be added onInsert. See https://github.com/CityWebConsultants/Iris/pull/266 for an example. Or add them server side.

There needs to be a way for modules to extend the list of widgets available to this new selector, such as ckeditor, ace etc.

For custom forms or form overrides, you would add this feature to textareas but setting the field widget as something like:

data.form = [{
    "key" : "mytextarea",
    "type" : "multiwidget",
}];

For entities, the Long text field would have an extra widget available 'Multi-widget' or something similar. The settings for this widget would allow the admin to choose which of widgets should be made available to the end user.

FilipNest commented 8 years ago

Seems to make sense. Looks good.