/[drupal]/contributions/modules/htmlbox/htmlbox.module
ViewVC logotype

Contents of /contributions/modules/htmlbox/htmlbox.module

Parent Directory Parent Directory | Revision Log Revision Log | View Revision Graph Revision Graph


Revision 1.11 - (show annotations) (download) (as text)
Thu Jul 17 20:53:24 2008 UTC (16 months, 1 week ago) by poetro
Branch: MAIN
CVS Tags: HEAD
Changes since 1.10: +17 -13 lines
File MIME type: text/x-php
Updating to the latest and greatest
CSS fix for http://drupal.org/node/283346
New Drag-and-Drop feature to compose the Button order
Little JS fixes
1 <?php
2 /* $Id: htmlbox.module,v 1.1.2.2 2008/07/04 09:33:00 poetro Exp $ */
3
4 /**
5 * @file HTMLBox WYSIWYG editor
6 */
7
8 /**
9 * Implementation of hook_menu().
10 */
11 function htmlbox_menu($may_cache) {
12 $items = array();
13
14 if ($may_cache) {
15 $items[] = array(
16 'path' => 'admin/settings/htmlbox',
17 'title' => t('HTMLBox settings'),
18 'description' => t('Visibility and button configuration for the HTMLBox.'),
19 'callback' => 'drupal_get_form',
20 'callback arguments' => 'htmlbox_admin_settings',
21 'type' => MENU_NORMAL_ITEM,
22 );
23 }
24
25 return $items;
26 }
27
28 /**
29 * Implementation of hook_perm().
30 */
31 function htmlbox_perm() {
32 return array('access htmlbox');
33 }
34
35 /**
36 * Menu callback; display settings form.
37 * @return Form array.
38 */
39 function htmlbox_admin_settings() {
40 $form = array();
41
42 $form['display'] = array(
43 '#type' => 'fieldset',
44 '#title' => t('Display Settings'),
45 '#collapsible' => TRUE,
46 '#collapsed' => FALSE,
47 );
48
49 $form['display']['node_forms'] = array(
50 '#type' => 'fieldset',
51 '#title' => t('Node forms'),
52 '#collapsible' => TRUE,
53 '#collapsed' => FALSE,
54 );
55 $form['display']['node_forms']['htmlbox_node_forms'] = array(
56 '#type' => 'checkboxes',
57 '#title' => t('Node forms'),
58 '#description' => t('Display the HTMLBox on the node forms above.'),
59 '#options' => node_get_types('names'),
60 '#default_value' => variable_get('htmlbox_node_forms', array()),
61 );
62 $form['display']['node_forms']['htmlbox_node_forms_body_only'] = array(
63 '#type' => 'checkbox',
64 '#title' => t('Body only'),
65 '#description' => t('Display the HTMLBox only on the Body element.'),
66 '#default_value' => variable_get('htmlbox_node_forms_body_only', 0),
67 );
68
69 $form['display']['htmlbox_other_forms'] = array(
70 '#type' => 'checkboxes',
71 '#title' => t('Other forms'),
72 '#options' => array(
73 'comment_form' => t('Comment form'),
74 'contact_mail_page' => t('Site contact form'),
75 'contact_mail_user' => t('User contact form'),
76 'taxonomy_form_vocabulary' => t('Category Vocabulary form'),
77 'taxonomy_form_term' => t('Category Vocabulary term form'),
78 'any' => t('Any other textarea'),
79 ),
80 '#default_value' => variable_get('htmlbox_other_forms', array()),
81 );
82
83 $form['display']['htmlbox_custom_fields'] = array(
84 '#type' => 'textarea',
85 '#title' => t('Custom fields'),
86 '#description' => t('Comma separated textarea ids of the textareas to be converted to HTMLBox, specify it\'s ID. For example: <p><code>&lt;textarea class="form-textarea" id="edit-comment" name="comment" rows="15" cols="60"/&gt;</code></p> the id is <em>edit-comment</em>.'),
87 '#default_value' => variable_get('htmlbox_custom_fields', ''),
88 );
89
90
91 $buttons = _htmlbox_available_buttons();
92 $form['display']['htmlbox_buttons_order'] = array(
93 '#type' => 'textarea',
94 '#title' => t('Button Order'),
95 '#description' => t('Comma separated items from the options below. Use the words right next to the icons.') . theme('htmlbox_settings_item', $buttons),
96 '#default_value' => variable_get('htmlbox_buttons_order', 'bold, italic, separator_dots, hyperlink, separator_dots, ul, ol, code, separator_dots, indent, outdent, separator_dots'),
97 );
98
99 $form['options'] = array(
100 '#type' => 'fieldset',
101 '#title' => t('Options'),
102 '#collapsible' => TRUE,
103 '#collapsed' => TRUE,
104 );
105
106 $parser_available = is_readable(drupal_get_path('module', 'htmlbox') .'/htmlparser.js');
107 $form['options']['htmlbox_xhtml_parser'] = array(
108 '#type' => 'checkbox',
109 '#title' => t('Enable HTML to XHTML converter'),
110 '#description' => t('Allow the JavaScript HTML to XHTML converter. It can require more CPU power to convert the content from HTML to XHTML, which may cause the system to be less stable. Some browsers may do the conversion without using the client side JavaScript. !parser_available',
111 array(
112 '!parser_available' => $parser_available ? '' : t('To enable the XHTML converter, <a href="@download_link">donwload</a> it, and place it in the HTMLBox module\'s directory.', array('@download_link' => 'http://ejohn.org/files/htmlparser.js')),
113 )
114 ),
115 '#default_value' => variable_get('htmlbox_xhtml_parser', 0),
116 '#attributes' => $parser_available ? array() : array('disabled' => 'disabled'),
117 );
118 $form['options']['htmlbox_newline_removal'] = array(
119 '#type' => 'checkbox',
120 '#title' => t('Enable newline removal'),
121 '#description' => t('Allow new lines (line breaks) to be removed from the (X)HTML output of the HTMLBox area. HTML new lines (&lt;br&gt;) will not be removed.'),
122 '#default_value' => variable_get('htmlbox_newline_removal', 1),
123 '#attributes' => $parser_available ? array() : array('disabled' => 'disabled'),
124 );
125
126 drupal_add_css(drupal_get_path('module', 'htmlbox') .'/htmlbox-admin.css');
127 drupal_add_js(drupal_get_path('module', 'htmlbox') .'/htmlbox-admin.js');
128 drupal_add_js(array('htmlbox' => array('order_description' => t('Drag and drop items into, and out of the box. The items can also be rearranged. The items inside the box will be used as the buttons of the HTMLBox in the same order as they appear in there.'))), 'setting');
129 return system_settings_form($form);
130 }
131
132 /**
133 * Helper function; get available buttons.
134 * @return Available HTMLBox buttons in an array.
135 */
136 function _htmlbox_available_buttons() {
137 return array(
138 // Inline formatting
139 'bold' => t('Bold'),
140 'italic' => t('Italic'),
141 'underline' => t('Underline'),
142 'sup' => t('Superscript'),
143 'sub' => t('Subscript'),
144
145 // Clipboard related
146 'cut' => t('@option (may not work in every browser, experimental)', array('@option' => t('Cut'))),
147 'copy' => t('@option (may not work in every browser, experimental)', array('@option' => t('Copy'))),
148 'paste' => t('@option (may not work in every browser, experimental)', array('@option' => t('Paste'))),
149 'undo' => t('@option (may not work in every browser, experimental)', array('@option' => t('Undo'))),
150 'redo' => t('@option (may not work in every browser, experimental)', array('@option' => t('Redo'))),
151
152 // Align
153 'left' => t('Superscript'),
154 'right' => t('Subscript'),
155 'center' => t('Superscript'),
156 'justify' => t('Subscript'),
157
158 // Lists / blocks
159 'ol' => t('Ordered list'),
160 'ul' => t('Unordered list'),
161 'indent' => t('Indent'),
162 'outdent' => t('Outdent'),
163 'p' => t('Paragraph'),
164 'pre' => t('Preformatted'),
165 'code' => t('Code'),
166 'headers' => t('Headers (H1-H6)'),
167
168 // Inline elements
169 'hyperlink' => t('Link'),
170 'image' => t('Image'),
171
172 // Font changes
173 'fontsize' => t('Font size'),
174 'fontfamily' => t('Font family'),
175 'fontcolor' => t('Text color'),
176 'highlight' => t('Background color'),
177
178 // Misc
179 'html' => t('HTML source'),
180 'separator_basic' => t('Basic Separators'),
181 'separator_dots' => t('Dotted Separators'),
182 );
183 }
184
185 /**
186 * Render HTMLBox settings page item listing.
187 * @param $buttons Associated array of available buttons.
188 * @return Themed list of items.
189 */
190 function theme_htmlbox_settings_item($buttons) {
191 $output = '<div class="htmlbox-buttons"><dl>';
192 foreach ($buttons as $item => $desc) {
193 $output .= '<dt><span class="htmlbox-'. $item .'" title="'. $desc .'"></span> '. $item .'</dt>';
194 $output .= '<dd>'. $desc .'</dd>';
195 }
196 $output .= '</dl></div>';
197 return $output;
198 }
199
200 /**
201 * Prepare the JavaScript to be added for each element.
202 * @return JavaScript code.
203 */
204 function htmlbox_js_settings() {
205 $options = explode(',', variable_get('htmlbox_buttons_order',
206 'bold, italic, separator_dots, hyperlink, separator_dots, ul, ol, html, separator_dots, indent, outdent, separator_dots'));
207 if (count($options)) {
208 $js = '';
209 $buttons = _htmlbox_available_buttons();
210 foreach ($options as $option) {
211 $option = trim($option);
212 // Only add valid buttons
213 if (array_key_exists($option, $buttons)) {
214 $js .= '.button("'. $option .'")';
215 }
216 }
217 if (!empty($js)) {
218 $js = '$(this).htmlbox()'. $js .'.init();';
219 return $js;
220 }
221 }
222 return '';
223 }
224
225 /**
226 * Prepare HTMLBox attachment.
227 * @param $area Id of form element to attach the editor to.
228 * @return Array of ids the HTMLBox is attached to.
229 */
230 function htmlbox_js_attach_editor($area = NULL) {
231 static $areas;
232 // Add the needed CSS and JS files.
233 if (!isset($areas)) {
234 drupal_add_css(drupal_get_path('module', 'htmlbox') .'/htmlbox.css');
235 drupal_add_js(drupal_get_path('module', 'htmlbox') .'/htmlbox.js');
236 if (variable_get('htmlbox_xhtml_parser', 0)) {
237 $parser = drupal_get_path('module', 'htmlbox') .'/htmlparser.js';
238 if (is_readable($parser)) {
239 drupal_add_js($parser);
240 }
241 }
242 drupal_add_js(array('htmlbox' => array('newline_removal' => variable_get('htmlbox_newline_removal', 1) == 1)), 'setting');
243
244 // Add custom textareas, as this is the initial point to add any
245 $areas = array();
246 if ($fields = variable_get('htmlbox_custom_fields', '')) {
247 $fields = explode(',', $fields);
248 foreach ($fields as $field) {
249 $field = trim($field);
250 // Add only valid IDs
251 if ($field && preg_match('!^[a-z][a-z\pL0-9:.\[\]_\-]*$!i', $field)) {
252 $areas[] = $field;
253 }
254 }
255
256 }
257 }
258 if (!empty($area)) {
259 $areas[] = $area;
260 }
261 return $areas;
262 }
263
264 /**
265 * Implementation of hook_form_alter().
266 * Attach HTMLBox to various textareas.
267 */
268 function htmlbox_form_alter($form_id, &$form) {
269 if (user_access('access htmlbox')) {
270 $attach_to = '';
271 $other_forms = array_filter(variable_get('htmlbox_other_forms', array()));
272 $node_forms = array_filter(variable_get('htmlbox_node_forms', array()));
273 $possible_forms = array(
274 'comment_form',
275 'contact_mail_page',
276 'contact_mail_user',
277 'taxonomy_form_vocabulary',
278 'taxonomy_form_term',
279 );
280
281 if ($other_forms['any'] && $form['#id'] != 'node-form' && !in_array($form_id, $possible_forms)) {
282 // Prepare the form for build to have all the names we need.
283 $built = form_builder($form_id, $form);
284 $attach_to = _htmlbox_textarea_search($built);
285 }
286 else if ($form['#id'] == 'node-form' && array_key_exists($form['type']['#value'], $node_forms)) {
287 if (variable_get('htmlbox_node_forms_body_only', 0)) {
288 $attach_to = 'edit-body';
289 }
290 else {
291 // Prepare the form for build to have all the names we need.
292 $built = form_builder($form_id, $form);
293 $attach_to = _htmlbox_textarea_search($built);
294 }
295 }
296 else if (array_key_exists($form_id, $other_forms)) {
297 // Prepare to handle custom forms
298 switch ($form_id) {
299 case 'comment_form':
300 $attach_to = 'edit-comment';
301 break;
302 case 'contact_mail_page':
303 case 'contact_mail_user':
304 $attach_to = 'edit-message';
305 break;
306 case 'taxonomy_form_vocabulary':
307 case 'taxonomy_form_term':
308 $attach_to = 'edit-description';
309 default:
310 break;
311 }
312 }
313
314 if (!empty($attach_to)) {
315 if (is_array($attach_to)) {
316 foreach ($attach_to as $item) {
317 htmlbox_js_attach_editor($item);
318 }
319 }
320 else {
321 htmlbox_js_attach_editor($attach_to);
322 }
323 }
324 }
325 }
326
327 /**
328 * Search for textareas in the form.
329 * @return Array of textarea ids.
330 */
331 function _htmlbox_textarea_search($elements) {
332 $textareas = array();
333 if (!isset($elements['#children'])) {
334 // If we have children, do a recursive search
335 $children = element_children($elements);
336 foreach ($children as $key) {
337 if ($areas = _htmlbox_textarea_search($elements[$key])) {
338 $textareas = array_merge($textareas, $areas);
339 }
340 }
341
342 // Add the found textare IDs to the list
343 if ($elements['#type'] == 'textarea') {
344 $textareas[] = $elements['#id'];
345 }
346 }
347 return $textareas;
348 }
349
350 /**
351 * Implementation of hook_footer().
352 */
353 function htmlbox_footer() {
354 if ($areas = htmlbox_js_attach_editor()) {
355 if (count($areas) && $js = htmlbox_js_settings()) {
356 // Prepare CSS IDs from the given list of textareas, only include unique IDs
357 $items = '#'. implode(', #', array_unique($areas));
358 drupal_add_js('$(function () { $("'. $items .'").each(function () {'. $js .'})});', 'inline', 'footer');
359 }
360 }
361 }

  ViewVC Help
Powered by ViewVC 1.1.2