comparison core/modules/ckeditor/js/views/VisualView.es6.js @ 0:c75dbcec494b

Initial commit from drush-created site
author Chris Cannam
date Thu, 05 Jul 2018 14:24:15 +0000
parents
children a9cd425dd02b
comparison
equal deleted inserted replaced
-1:000000000000 0:c75dbcec494b
1 /**
2 * @file
3 * A Backbone View that provides the visual UX view of CKEditor toolbar
4 * configuration.
5 */
6
7 (function (Drupal, Backbone, $) {
8 Drupal.ckeditor.VisualView = Backbone.View.extend(/** @lends Drupal.ckeditor.VisualView# */{
9
10 events: {
11 'click .ckeditor-toolbar-group-name': 'onGroupNameClick',
12 'click .ckeditor-groupnames-toggle': 'onGroupNamesToggleClick',
13 'click .ckeditor-add-new-group button': 'onAddGroupButtonClick',
14 },
15
16 /**
17 * Backbone View for CKEditor toolbar configuration; visual UX.
18 *
19 * @constructs
20 *
21 * @augments Backbone.View
22 */
23 initialize() {
24 this.listenTo(this.model, 'change:isDirty change:groupNamesVisible', this.render);
25
26 // Add a toggle for the button group names.
27 $(Drupal.theme('ckeditorButtonGroupNamesToggle'))
28 .prependTo(this.$el.find('#ckeditor-active-toolbar').parent());
29
30 this.render();
31 },
32
33 /**
34 * Render function for rendering the toolbar configuration.
35 *
36 * @param {*} model
37 * Model used for the view.
38 * @param {string} [value]
39 * The value that was changed.
40 * @param {object} changedAttributes
41 * The attributes that was changed.
42 *
43 * @return {Drupal.ckeditor.VisualView}
44 * The {@link Drupal.ckeditor.VisualView} object.
45 */
46 render(model, value, changedAttributes) {
47 this.insertPlaceholders();
48 this.applySorting();
49
50 // Toggle button group names.
51 let groupNamesVisible = this.model.get('groupNamesVisible');
52 // If a button was just placed in the active toolbar, ensure that the
53 // button group names are visible.
54 if (changedAttributes && changedAttributes.changes && changedAttributes.changes.isDirty) {
55 this.model.set({ groupNamesVisible: true }, { silent: true });
56 groupNamesVisible = true;
57 }
58 this.$el.find('[data-toolbar="active"]').toggleClass('ckeditor-group-names-are-visible', groupNamesVisible);
59 this.$el.find('.ckeditor-groupnames-toggle')
60 .text((groupNamesVisible) ? Drupal.t('Hide group names') : Drupal.t('Show group names'))
61 .attr('aria-pressed', groupNamesVisible);
62
63 return this;
64 },
65
66 /**
67 * Handles clicks to a button group name.
68 *
69 * @param {jQuery.Event} event
70 * The click event on the button group.
71 */
72 onGroupNameClick(event) {
73 const $group = $(event.currentTarget).closest('.ckeditor-toolbar-group');
74 Drupal.ckeditor.openGroupNameDialog(this, $group);
75
76 event.stopPropagation();
77 event.preventDefault();
78 },
79
80 /**
81 * Handles clicks on the button group names toggle button.
82 *
83 * @param {jQuery.Event} event
84 * The click event on the toggle button.
85 */
86 onGroupNamesToggleClick(event) {
87 this.model.set('groupNamesVisible', !this.model.get('groupNamesVisible'));
88 event.preventDefault();
89 },
90
91 /**
92 * Prompts the user to provide a name for a new button group; inserts it.
93 *
94 * @param {jQuery.Event} event
95 * The event of the button click.
96 */
97 onAddGroupButtonClick(event) {
98 /**
99 * Inserts a new button if the openGroupNameDialog function returns true.
100 *
101 * @param {bool} success
102 * A flag that indicates if the user created a new group (true) or
103 * canceled out of the dialog (false).
104 * @param {jQuery} $group
105 * A jQuery DOM fragment that represents the new button group. It has
106 * not been added to the DOM yet.
107 */
108 function insertNewGroup(success, $group) {
109 if (success) {
110 $group.appendTo($(event.currentTarget).closest('.ckeditor-row').children('.ckeditor-toolbar-groups'));
111 // Focus on the new group.
112 $group.trigger('focus');
113 }
114 }
115
116 // Pass in a DOM fragment of a placeholder group so that the new group
117 // name can be applied to it.
118 Drupal.ckeditor.openGroupNameDialog(this, $(Drupal.theme('ckeditorToolbarGroup')), insertNewGroup);
119
120 event.preventDefault();
121 },
122
123 /**
124 * Handles jQuery Sortable stop sort of a button group.
125 *
126 * @param {jQuery.Event} event
127 * The event triggered on the group drag.
128 * @param {object} ui
129 * A jQuery.ui.sortable argument that contains information about the
130 * elements involved in the sort action.
131 */
132 endGroupDrag(event, ui) {
133 const view = this;
134 Drupal.ckeditor.registerGroupMove(this, ui.item, (success) => {
135 if (!success) {
136 // Cancel any sorting in the configuration area.
137 view.$el.find('.ckeditor-toolbar-configuration').find('.ui-sortable').sortable('cancel');
138 }
139 });
140 },
141
142 /**
143 * Handles jQuery Sortable start sort of a button.
144 *
145 * @param {jQuery.Event} event
146 * The event triggered on the group drag.
147 * @param {object} ui
148 * A jQuery.ui.sortable argument that contains information about the
149 * elements involved in the sort action.
150 */
151 startButtonDrag(event, ui) {
152 this.$el.find('a:focus').trigger('blur');
153
154 // Show the button group names as soon as the user starts dragging.
155 this.model.set('groupNamesVisible', true);
156 },
157
158 /**
159 * Handles jQuery Sortable stop sort of a button.
160 *
161 * @param {jQuery.Event} event
162 * The event triggered on the button drag.
163 * @param {object} ui
164 * A jQuery.ui.sortable argument that contains information about the
165 * elements involved in the sort action.
166 */
167 endButtonDrag(event, ui) {
168 const view = this;
169 Drupal.ckeditor.registerButtonMove(this, ui.item, (success) => {
170 if (!success) {
171 // Cancel any sorting in the configuration area.
172 view.$el.find('.ui-sortable').sortable('cancel');
173 }
174 // Refocus the target button so that the user can continue from a known
175 // place.
176 ui.item.find('a').trigger('focus');
177 });
178 },
179
180 /**
181 * Invokes jQuery.sortable() on new buttons and groups in a CKEditor config.
182 */
183 applySorting() {
184 // Make the buttons sortable.
185 this.$el.find('.ckeditor-buttons').not('.ui-sortable').sortable({
186 // Change this to .ckeditor-toolbar-group-buttons.
187 connectWith: '.ckeditor-buttons',
188 placeholder: 'ckeditor-button-placeholder',
189 forcePlaceholderSize: true,
190 tolerance: 'pointer',
191 cursor: 'move',
192 start: this.startButtonDrag.bind(this),
193 // Sorting within a sortable.
194 stop: this.endButtonDrag.bind(this),
195 }).disableSelection();
196
197 // Add the drag and drop functionality to button groups.
198 this.$el.find('.ckeditor-toolbar-groups').not('.ui-sortable').sortable({
199 connectWith: '.ckeditor-toolbar-groups',
200 cancel: '.ckeditor-add-new-group',
201 placeholder: 'ckeditor-toolbar-group-placeholder',
202 forcePlaceholderSize: true,
203 cursor: 'move',
204 stop: this.endGroupDrag.bind(this),
205 });
206
207 // Add the drag and drop functionality to buttons.
208 this.$el.find('.ckeditor-multiple-buttons li').draggable({
209 connectToSortable: '.ckeditor-toolbar-active .ckeditor-buttons',
210 helper: 'clone',
211 });
212 },
213
214 /**
215 * Wraps the invocation of methods to insert blank groups and rows.
216 */
217 insertPlaceholders() {
218 this.insertPlaceholderRow();
219 this.insertNewGroupButtons();
220 },
221
222 /**
223 * Inserts a blank row at the bottom of the CKEditor configuration.
224 */
225 insertPlaceholderRow() {
226 let $rows = this.$el.find('.ckeditor-row');
227 // Add a placeholder row. to the end of the list if one does not exist.
228 if (!$rows.eq(-1).hasClass('placeholder')) {
229 this.$el
230 .find('.ckeditor-toolbar-active')
231 .children('.ckeditor-active-toolbar-configuration')
232 .append(Drupal.theme('ckeditorRow'));
233 }
234 // Update the $rows variable to include the new row.
235 $rows = this.$el.find('.ckeditor-row');
236 // Remove blank rows except the last one.
237 const len = $rows.length;
238 $rows.filter((index, row) => {
239 // Do not remove the last row.
240 if (index + 1 === len) {
241 return false;
242 }
243 return $(row).find('.ckeditor-toolbar-group').not('.placeholder').length === 0;
244 })
245 // Then get all rows that are placeholders and remove them.
246 .remove();
247 },
248
249 /**
250 * Inserts a button in each row that will add a new CKEditor button group.
251 */
252 insertNewGroupButtons() {
253 // Insert an add group button to each row.
254 this.$el.find('.ckeditor-row').each(function () {
255 const $row = $(this);
256 const $groups = $row.find('.ckeditor-toolbar-group');
257 const $button = $row.find('.ckeditor-add-new-group');
258 if ($button.length === 0) {
259 $row.children('.ckeditor-toolbar-groups').append(Drupal.theme('ckeditorNewButtonGroup'));
260 }
261 // If a placeholder group exists, make sure it's at the end of the row.
262 else if (!$groups.eq(-1).hasClass('ckeditor-add-new-group')) {
263 $button.appendTo($row.children('.ckeditor-toolbar-groups'));
264 }
265 });
266 },
267 });
268 }(Drupal, Backbone, jQuery));