Allow to sort editor buttons
| Project: | Wysiwyg |
| Version: | 6.x-1.x-dev |
| Component: | User interface |
| Category: | feature request |
| Priority: | normal |
| Assigned: | sun |
| Status: | needs work |
I have made a few changes to the wysiwyg_editor.module file to improve the configuration of buttons and:
- be able to split the buttons of plugins, and order them flexibly (mainly for the default plugins)
- be able to use the | separator
These changes are backward compatible, the previous configuration files should still be read correctly.
Here is an excerpt from my new configuration file:
<?php
$plugins['default']['theme_advanced_buttons2-01'] = array('cut', 'copy', 'paste');
$plugins['paste'] = array();
$plugins['paste']['theme_advanced_buttons2-02'] = array('pastetext', 'pasteword', 'selectall','|');
$plugins['default']['theme_advanced_buttons2-031'] = array('undo', 'redo', '|');
$plugins['default']['theme_advanced_buttons2-032'] = array('justifyleft', 'justifycenter', 'justifyright', 'justifyfull', '|');
$plugins['default']['theme_advanced_buttons2-033'] = array('bullist', 'numlist', 'outdent', 'indent', '|');
?>This example shows how I have grouped all the "paste" buttons together, whether they come from the default plugin or from the "paste" plugin.
The new syntax is pretty simple:
- add
'|'to insert a separator - groups of buttons are defined by
theme_advanced_buttons#????, where # is the button row number (1, 2 or 3) and ???? is a string which names the group of buttons
The button groups are inserted in the order of their names (order as string).
The changes I made are quite simple:
<?php
foreach ($mce_value as $k => $v) {
// Add a separator
if ($v == '|'){
$init[$mce_key][] = $v;
}
elseif (isset($settings['buttons'][$rname .'-'. $v])) {
// Font isn't a true plugin, rather it's buttons made available by the advanced theme
if (!in_array($rname, $plugin_tracker) && $rname != 'font') {
$plugin_tracker[] = $rname;
}
// record the subgroups
if (substr($mce_key,0,22)=='theme_advanced_buttons') {
$group_id = substr($mce_key,22); // strlrn('theme_advanced_buttons')= 22
$button_groups[$group_id]=$mce_key;
}
$init[$mce_key][] = $v;
}
}
?>and
<?php
if (!isset($init['theme_advanced_buttons3'])) {
$init['theme_advanced_buttons3'] = array();
}
// sort the IDs of button groups
ksort($button_groups, SORT_STRING);
foreach($button_groups as $group_id => $key){
if (strlen($group_id)>1){
// merge buttons subgroups into the relevant button bar
$bar_key = 'theme_advanced_buttons' . substr($group_id,0,1);
$init[$bar_key] = array_merge($init[$bar_key], $init[$key]);
$init[$key] = array();
}
}
// Minimum number of buttons per row.
$min_btns = 5;
?>Sorry I am quite new to Drupal, and I cannot make a proper patch. I attach my new files.
Please let me know what you think of these changes...
I have a question: is it possible to override _wysiwyg_editor_plugins() in a theme? how?
| Attachment | Size |
|---|---|
| wysiwyg_editor.module.zip | 8.05 KB |

#1
This sounds good, but I'm unable to review what you have done. Please have a look at http://drupal.org/patch or particularly http://drupal.org/patch/create.
Also, latest code in CVS no longer arranges buttons in multiple rows; it's using CSS to align all buttons in row instead.
#2
I'll try to post a patch. However I have to install the diff tools.
However I do not understand what you have done in the CVS version. Removing the ability to arrange buttons on several rows is a huge regression in term of customization. There are just too many buttons to arrange on a single row.
Does your solution somehow "wrap" a row if it is too long?
You said that you are using CSS to align the buttons in the row. Does it enable to order the buttons in the row? Is there a discussion describing these changes?
#3
No, it does not allow to change the order of buttons in a row. But that was also not possible before. The long-term goal for Wysiwyg Editor is to allow the administrator to re-arrange the enabled buttons/plugins in a GUI via jQuery UI sortables, just like JCE for Joomla! (there seems to be no public demo, but I can tell you it's fun to move buttons via drag'n'drop).
#4
I agree with you on the target of the GUI. What is the purpose of the changes you have made in the CVS? Is it a step to meet the requirements for the GUI?
Obviously these changes in the CVS will not work with mine.
I was trying to enable a (simple) way to configure the buttons from a configuration file. Here is what I would propose to implement the same kind of functionality with the new CVS:
wysiwyg_editor.plugins.incfile, add a "button group default" information to the buttons, eg.<?php'buttons' => array('ltr' => array('title'=>t('Left-to-right'), 'default-pos'=>'2-03-01'), 'rtl' => array('title'=>t('Right-to-left'), 'default-pos'=>'2-03-01')),
?>
Here I used a position naming scheme such as #-&&-?? with #=button bar number (1 to 3), && = button group number and ??=button position in group
wysiwyg_editor.admin.incgenerate the buttons bars based on the bar/group/position, with | between groups of buttonswysiwyg_editor.admin.incadd a text input form to modify the button position (optional)What do you think of this?
#5
Well, the ordinary audience of this module does not even know how to pronounce "configuration file". So better forget this plan rather sooner than later.
Also, Wysiwyg [Editor] module (and most notably hook_wysiwyg_plugin()) was developed to remove the need of editing of configuration files. If we would implement hard-coded button "weights" like you propose, site admins would have to edit plenty of module files to get the buttons in the order they want. Please read #152046: hook_wysiwyg_plugin() for further information.
#6
My last bullet proposed to add a text input in the Wysiwyg config page in addition to the checkbox to enable a button. This text input would enable the input of the order of buttons without modifying the config file. The config file would just provide the defaults values.
Of course this text input is less "user friendly" than a drag and drop solution, but it would be easier to implement, and a step toward the AJAX solution.
#7
Well, implementing this via jQuery UI should be fairly easy. All we need is the list of buttons in the desired order.
I could imagine two ways of doing this: Either allow the user to sort directly in the button list (where the checkboxes are), or introduce a new fieldset which contains the sort interface.
Technically, I could imagine three ways of storing the order: Either by re-arranging and submitting the buttons in the form already in the right order (that would be the simplest, but might also be the most error-prone way), or add another fieldset which contains the enabled buttons only and additionally submit button => weight pairs (IIRC, ui.sortable provides this already). The 3rd way would be to add a hidden weight field to each button, allowing the user to sort in either of the preceding ways, and store the new weight of each button in the hidden field.
We've implemented something similar for ImageField recently, see #264162: Allow to sort multiple images and #264171: Use jQuery UI for drag'n'drop sorting of images
#8
Better title.
#9
I would love to see an ajax drag and drop UI to order button as you want, like CCK, block or menu provide (in drupal 6).
/Subscribe
#10
smk-ka worked on this and showed me a working preview already. Assigning to myself, so we are not running into duplicated efforts. However, a patch will probably not make sense until #319363: Rewrite editor plugin API has landed.
#11
See yui editor for a decent approach to this:
1. Focus the drag on and drop on adding and removing buttons
2. Try to keep similar buttons in groups. Why would you want to move an italicize to another row, on the opposite side of bold, and underline?
#12
Some quick notes about the current considerations:
- Buttons will be sortable via jQuery UI.
- You can place buttons into multiple rows in the toolbar.
- We need a way to allow users to insert button separators into the toolbar. This will probably be handled through a simple link "Add separator", which adds a separator "button" into the layouter.
- After adding a separator, a user may want to remove it. So we need a way to remove a particular separator "button" from the toolbar.
- That could be done by implementing a drop area, which removes a separator "button" from the toolbar.
- But then again, the question arose why we do not simply implement 2 toolbars - one containing all available buttons, and the other containing all enabled buttons. By dragging a button from the available to the enabled toolbar, it is enabled for the profile. By dragging a button from the enabled to the available toolbar, it is disabled.
- The same would work intuitively for separators. However, there would be an additional link between both toolbars that allows to spawn a new separator.
So this is the current plan:
1) Turn the current table containing checkboxes into a toolbar containing all "available" buttons.
2) Add a second "enabled" toolbar where buttons can be drag'n'dropped into and sorted.
3) Add a link between both toolbars to spawn a separator button into the enabled toolbar.
This will be the base for further, required improvements; specifically: Allowing to configure settings for each plugin/button. The current idea is to load a configuration form for a button via AJAX by double-clicking on it.
#13
Hey,
For about a year ago I created a module which enables administrators to create roles for TinyMCE's RTE. It was not only intended to serve node textfields while you could use jQuery selectors to attach TinyMCE to. It also provides admins a way to customize the toolbar by drag and drop. Because it's sort of similar to what's discussed here, I thought it would be wise to mention. I've put an example here. Note the plugin checkboxes are updated after a button is dropped.
#14
@skilip: Thanks - however, a demo video doesn't help much. If you have code to share, please attach it (uncompressed) to this issue.
#15
What do you mean with uncompressed?
#16
What do you mean by 'uncompressed'?
#17
"uncompressed" = single files, no archive (like tgz or zip)
#18
My apologies for the delay. Here are the files. Since they are D5 and from my early Drupal days, the code isn't state of the art.
The idea is simple; I've created a file in which all buttons are defined in an array. The skins and plugins are fetched with a readdir. This file is included in the profile's settings pages.
The plugin / button array is stored in a hidden input element (in json format) and then picked up by javascript. Every time the order of the toolbar changes, the value of the hidden input field is updated. After submitting the form, the new order is stored with the profile.
@sun: You asked me to attach the files uncompressed. While it isn't possible to attach js files here, I zipped the module anyway. Sorry if didn't understand you correctly.
#19
Does anyone know of a thread on...
1) How to sort plugin buttons in Version 6.x?
2) How to add and enable plugins in Version 6.x?
#20
Oh, you are right - assigning proper version (new features go always into the latest version first). However, aside from that, Wysiwyg API has almost no differences between 5.x and 6.x.
#21
I am confused though because I do not see "wysiwyg_editor.module" or "wysiwyg_editor.plugins.inc" in the 6.x module so I'm not sure where Andjety's changes apply to...
#22
"wysiwyg_editor" was basically just renamed to "wysiwyg". However, since that happened some time ago, it is also possible that parts of the code/patch can no longer be applied properly.
#23
Okay, I'm not a PHP and coding whiz and from what I see, yes, the code seems entirely different than what is present in the latest 6.x module. I'll stand aside for now until someone can take a serious look at this issue and have the sorting work out for 6.x! >.<
#24
Here's a Wordpress plugin that might be able to be used as a basis for this feature:
http://wordpress.org/extend/plugins/wp-super-edit/screenshots/
#25
Subscribing to this thread.
My Web site's layout was getting screwed up by having too many buttons on one row. I ended up modifying the code in editors/tinymce.inc at around line 250.
Original code:
<?phpfor ($i = 0; $i < count($init['buttons']); $i++) {
$init['theme_advanced_buttons1'][] = $init['buttons'][$i];
}
?>
Modified code:
<?php$row = 1;
for ($i = 0; $i < count($init['buttons']); $i++) {
$rowi++;
if($rowi > variable_get('wysiwyg_buttons_per_row', 21)) {
$rowi = 0;
$row++;
}
$init['theme_advanced_buttons' . $row][] = $init['buttons'][$i];
}
?>
Now, if a toolbar has more than 22 buttons on a row (or more than the number you specified in settings.php file for the wysiwyg_buttons_per_row variable), the buttons will be moved on the next toolbar. The WYSIWYG now has a reasonable width and is no longer "breaking out" of my site's layout.
This is only meant to be a temporary solution for anyone who needs a quick fix. This is not fit for the permanent solution proposed in this thread.
Another one described the problem I was having at the following address:
http://drupal.org/node/98958
#26
subscribe
#27
I've implemented this fix and although it succeeds in breaking after the right amount of buttons, it throws up another problem.
After my first 11 buttons I have the "Table" check box selected, but instead of displaying the Table buttons it just displays four separators.
I'm going to try this instead: http://drupal.org/node/308912
#28
The same thing is happening with the other fix. Can anyone advise as to why?
Thanks.
edit: The Table buttons display in Chrome but not in IE6,7,8 or in FF2 and 3.
#29
I started from scratch and somehow eliminated this issue.
Thanks for the fix, remi!
#30
No problem. However, keep in mind that my fix is only a temporary solution before a permanent solution is perfected by the other people in this thread, which is already in the works.
#31
How about using the drag and drop interface we have ready to use in D6? Like the menu config pages, cck fields and so on... disabled items are grey...
#32
I know that the current situation is not optimal. However, I do not want to waste time with a half-baked solution.
Next to the envisioned UI in #12, this issue is slightly depending on #313497-13: Allow to configure advanced editor settings, which explains further details of how the final wysiwyg profile configuration will work. That needs a lot of work and deep insights into CTools though.
#33
Why depending on CTools? I hope you do not really need it... It haven't been build on jQuery and have other buggy stuff like a broken modal window library no more maintained since ~2 years or more :-(.
#34
Subscribing
#35
subscribing
#36
@sun:
1) I wonder if it is ok to use jQuery UI sortables to achieve this?
- http://jqueryui.com/demos/sortable/
- http://drupal.org/project/jquery_ui
Also, a couple more questions:
2) how many lines of buttons are available per editor? Is there something about it in the editor packages?
3) how the order of the buttons should be stored in the {wysiwyg} table?
#37
1) Yes, jQuery UI's sortable is the way to go.
2) Unlimited. Which can mean zero or 1,000.
3) We want to order the buttons only once, so they have to be re-arranged in the form submit handler, before DB storage.
#38
So what is the status of this? How can sort my TinyMCE buttons and arrange them into rows?
#39
I'm not sure "when", but if I have a hole, I'll try to write something. Anyone else is more than welcome to chime in, though. Now that we have specs (see #36/#37 above), it shouldn't be too hard. :P
BTW, if jQuery UI is going to be used here, then I would suggest doing so with 1.7.1 or higher. That requires latest snapshot of jquery_update 6.x-2.x-dev, and jquery_ui module with the proper library installed. See comment #64 in #358082: jQuery 1.3 in Drupal 6.x
#40
@markus_petrux I'm much willing to help here. As you can see by watching the video I've linked to in #13, I've got some experience with the drag and drop sorting of TinyMCE toolbars. Would it be possible to meet in IRC this weekend?
#41
@skilip: Sweet. Thought, I'm not sure of when I'll be able to spend time on this. I'll have to find holes here and there...
Aside from what sun posted in #37, we need to know:
4) Is there a common method in Wysiwyg API to obtain the paths to the button icons?
5) How do we store the button information in the {wysiwyg} table? We need to know, not only which buttons are enabled, but also the lines and position of them in the button bar of the editor. Any recommendation on this?
6) Finally, the implementation of this feature will have to provide a hook_update() method to migrate existing profiles.
#42
subscribe. much want me do.
#43
Subscribe. Will take a KISS solution ...
#44
subscribe
#45
Subscribing. I would really appreciate this function.
#46
subscribe
#47
subcribing to this.. it's an important feature.
#48
Subscribing. This is too important not to be in the wysiwyg module. One reason why I'm using tinytinymce instead of the wysiwyg (tinymce) at the moment.