--- /dev/null 2011-05-14 19:40:12.891427673 -0400 +++ editors/codemirror.inc 2011-05-15 07:13:26.761727527 -0400 @@ -0,0 +1,166 @@ + 'CodeMirror', + 'vendor url' => 'http://codemirror.net', + 'download url' => 'http://codemirror.net', + 'library path' => wysiwyg_get_path('codemirror'), + 'libraries' => array( + '' => array( + 'title' => 'Source', + 'files' => array( + 'lib/codemirror.js', + 'mode/clike/clike.js', + 'mode/css/css.js', + 'mode/diff/diff.js', + 'mode/haskell/haskell.js', + 'mode/htmlmixed/htmlmixed.js', + 'mode/javascript/javascript.js', + 'mode/php/php.js', + 'mode/stex/stex.js', + 'mode/xml/xml.js', + + ), + ), + ), + 'version callback' => 'wysiwyg_codemirror_version', + 'settings callback' => 'wysiwyg_codemirror_settings', + 'plugin callback' => 'wysiwyg_codemirror_plugins', + 'load callback' => 'wysiwyg_codemirror_load', + 'versions' => array( + '2.0' => array( + 'js files' => array('codemirror.js'), + ), + ), + ); + return $editor; +} + +/** + * Detect editor version. + * + * @param $editor + * An array containing editor properties as returned from hook_editor(). + * + * @return + * The installed editor version. + */ +function wysiwyg_codemirror_version($editor) { + return '2.0'; +} + +/** + * Perform additional actions upon loading this editor. + * + * @param $editor + * A processed hook_editor() array of editor properties. + * @param $library + * The internal library name (array key) to use. + */ +function wysiwyg_codemirror_load($editor, $library){ + drupal_add_css($editor['library path'] . '/lib/codemirror.css'); + foreach (glob($editor['library path'] . '/mode/*/*.css') as $css_file) { + drupal_add_css($css_file); + } +} +/** + * Return runtime editor settings for a given wysiwyg profile. + * + * @param $editor + * A processed hook_editor() array of editor properties. + * @param $config + * An array containing wysiwyg editor profile settings. + * @param $theme + * The name of a theme/GUI/skin to use. + * + * @return + * A settings array to be populated in + * Drupal.settings.wysiwyg.configs.{editor} + */ +function wysiwyg_codemirror_settings($editor, $config, $theme) { + /* Defaults */ + $codemirror_options = array( + 'mode' => array('name' => 'php'), + 'indentUnit' => 8, + 'indentWithTabs' => false, + 'tabMode' => 'classic', + 'enterMode' => "indent", + 'electricChars' => false, + 'lineNumbers' => false, + 'firstLineNumber' => 1, + 'gutter' => false, + 'readOnly' => false, + 'matchBrackets' => false, + 'undoDepth' => 40, + ); + + $all_codemirror_options = array_keys($codemirror_options); + + if (is_array($config['buttons']['default'])) { + foreach ($config['buttons']['default'] as $key => $value) { + if ($value) { + if (in_array($key, $all_codemirror_options)) { + $codemirror_options[$key] = ($value != 0); + } + } + } + } + + $settings = array( + 'codemirror_options' => $codemirror_options, + 'codemirror_options' => $codemirror_options, + ); + + // Add editor content stylesheet. + if (isset($config['css_setting'])) { + if ($config['css_setting'] == 'theme') { + $css = path_to_theme() . '/style.css'; + if (file_exists($css)) { + $settings['externalCSS'] = base_path() . $css; + } + } + else if ($config['css_setting'] == 'self' && isset($config['css_path'])) { + $settings['externalCSS'] = strtr($config['css_path'], array('%b' => base_path(), '%t' => path_to_theme())); + } + } + return $settings; +} + +/** + * Return internal plugins for this editor; semi-implementation of hook_wysiwyg_plugin(). + */ +function wysiwyg_codemirror_plugins($editor) { + return array( + 'default' => array( + /* Options Commented Out either don't make sense to set, + or are not Boolean options. Re-enabel them when WYSIWYG + supports non-boolean editor options. */ + 'buttons' => array( + /* CodeMirror Options */ + 'lineNumbers' => t('Line Numbers'), + 'matchBrackets' => t('Match Brackets'), +// 'indentUnit' => t("Indent Unit"), +// 'indentWithTabs' => t('Indent with Tabs'), +// 'mode' => t('Mode'), +// 'tabMode' => t('Tab Mode'), +// 'enterMode' => t('Enter Mode'), + 'electricChars' => t('Electric Characters'), +// 'firstLineNumber' => t('First Line Number'), +// 'gutter' => t('Gutter'), +// 'readOnly' => t('Read-Only'), +// 'undoDepth' => t('Undo depth'), + ), + ), + 'internal' => TRUE, + ); +} + --- /dev/null 2011-05-14 19:40:12.891427673 -0400 +++ editors/js/codemirror.js 2011-05-15 07:10:26.793482264 -0400 @@ -0,0 +1,67 @@ +(function($) { + +/* Maintain a list of active editors on the page */ +var codemirror_instances = new Object; + +/* A helper function to detatch and delete the editor going away. */ +function removeCodeMirrorEditor(editorId) { + codemirror_instances[editorId].toTextArea(); + delete codemirror_instances[editorId]; +} + +/** + * Attach this editor to a target element. + * + * @param context + * A DOM element, supplied by Drupal.attachBehaviors(). + * @param params + * An object containing input format parameters. Default parameters are: + * - editor: The internal editor name. + * - theme: The name/key of the editor theme/profile to use. + * - field: The CSS id of the target element. + * @param settings + * An object containing editor settings for all enabled editor themes. + */ +Drupal.wysiwyg.editor.attach.codemirror = function(context, params, settings) { + // Attach editor. +console.debug(settings); + var textArea = document.getElementById(params.field); + var editor = CodeMirror.fromTextArea(textArea, settings['codemirror_options']); + codemirror_instances[params.field] = editor; +}; + +/** + * Detach a single or all editors. + * + * @param context + * A DOM element, supplied by Drupal.attachBehaviors(). + * @param params + * (optional) An object containing input format parameters. If defined, + * only the editor instance in params.field should be detached. Otherwise, + * all editors should be detached and saved, so they can be submitted in + * AJAX/AHAH applications. + */ +Drupal.wysiwyg.editor.detach.codemirror = function(context, params) { + if (typeof params != 'undefined') { + removeCodeMirrorEditor(params.field); + } + else { + for (var editorId in codemirrors) { + removeCodeMirrorEditor(editorId); + } + } +}; + +/** + * Instance methods for codemirror. + */ +// Do I even need this? +/* +Drupal.wysiwyg.editor.instance.codemirror = { + insert: function(content) { + codemirrors[this.field].mirror.setValue(content); + } +}; +*/ + +})(jQuery);