dojo.provide("dijit._editor.RichText"); dojo.require("dijit._Widget"); dojo.require("dijit._editor.selection"); // used to save content // but do not try doing document.write if we are using xd loading. // document.write will only work if RichText.js is included in the dojo.js // file. If it is included in dojo.js and you want to allow rich text saving // for back/forward actions, then set djConfig.allowXdRichTextSave = true. if(!djConfig["useXDomain"] || djConfig["allowXdRichTextSave"]){ if(dojo._post_load){ (function(){ var savetextarea = dojo.doc.createElement('textarea'); savetextarea.id = "dijit._editor.RichText.savedContent"; var s = savetextarea.style; s.display='none'; s.position='absolute'; s.top="-100px"; s.left="-100px" s.height="3px"; s.width="3px"; dojo.body().appendChild(savetextarea); })(); }else{ //dojo.body() is not available before onLoad is fired try { dojo.doc.write(''); }catch(e){ } } } dojo.declare("dijit._editor.RichText", [ dijit._Widget ], { preamble: function(){ // summary: // dijit._editor.RichText is the core of the WYSIWYG editor in dojo, which // provides the basic editing features. It also encapsulates the differences // of different js engines for various browsers // contentPreFilters: Array // pre content filter function register array. // these filters will be executed before the actual // editing area get the html content this.contentPreFilters = []; // contentPostFilters: Array // post content filter function register array. // these will be used on the resulting html // from contentDomPostFilters. The resuling // content is the final html (returned by getValue()) this.contentPostFilters = []; // contentDomPreFilters: Array // pre content dom filter function register array. // these filters are applied after the result from // contentPreFilters are set to the editing area this.contentDomPreFilters = []; // contentDomPostFilters: Array // post content dom filter function register array. // these filters are executed on the editing area dom // the result from these will be passed to contentPostFilters this.contentDomPostFilters = []; // editingAreaStyleSheets: Array // array to store all the stylesheets applied to the editing area this.editingAreaStyleSheets=[]; this._keyHandlers = {}; this.contentPreFilters.push(dojo.hitch(this, "_preFixUrlAttributes")); if(dojo.isMoz){ this.contentPreFilters.push(this._fixContentForMoz); } //this.contentDomPostFilters.push(this._postDomFixUrlAttributes); this.onLoadDeferred = new dojo.Deferred(); }, // inheritWidth: Boolean // whether to inherit the parent's width or simply use 100% inheritWidth: false, // focusOnLoad: Boolean // whether focusing into this instance of richtext when page onload focusOnLoad: false, // name: String // If a save name is specified the content is saved and restored when the user // leave this page can come back, or if the editor is not properly closed after // editing has started. name: "", // styleSheets: String // semicolon (";") separated list of css files for the editing area styleSheets: "", // _content: String // temporary content storage _content: "", // height: String // set height to fix the editor at a specific height, with scrolling. // By default, this is 300px. If you want to have the editor always // resizes to accommodate the content, use AlwaysShowToolbar plugin // and set height="" height: "300px", // minHeight: String // The minimum height that the editor should have minHeight: "1em", // isClosed: Boolean isClosed: true, // isLoaded: Boolean isLoaded: false, // _SEPARATOR: String // used to concat contents from multiple textareas into a single string _SEPARATOR: "@@**%%__RICHTEXTBOUNDRY__%%**@@", // onLoadDeferred: dojo.Deferred // deferred that can be used to connect to the onLoad function. This // will only be set if dojo.Deferred is required onLoadDeferred: null, // Init postCreate: function(){ dojo.publish("dijit._editor.RichText::init", [this]); this.open(); this.setupDefaultShortcuts(); }, setupDefaultShortcuts: function(){ // summary: add some default key handlers // description: // Overwrite this to setup your own handlers. The default // implementation does not use Editor commands, but directly // executes the builtin commands within the underlying browser // support. var ctrl = this.KEY_CTRL; var exec = function(cmd, arg){ return arguments.length == 1 ? function(){ this.execCommand(cmd); } : function(){ this.execCommand(cmd, arg); } } this.addKeyHandler("b", ctrl, exec("bold")); this.addKeyHandler("i", ctrl, exec("italic")); this.addKeyHandler("u", ctrl, exec("underline")); this.addKeyHandler("a", ctrl, exec("selectall")); this.addKeyHandler("s", ctrl, function () { this.save(true); }); this.addKeyHandler("1", ctrl, exec("formatblock", "h1")); this.addKeyHandler("2", ctrl, exec("formatblock", "h2")); this.addKeyHandler("3", ctrl, exec("formatblock", "h3")); this.addKeyHandler("4", ctrl, exec("formatblock", "h4")); this.addKeyHandler("\\", ctrl, exec("insertunorderedlist")); if(!dojo.isIE){ this.addKeyHandler("Z", ctrl, exec("redo")); } }, // events: Array // events which should be connected to the underlying editing area events: ["onKeyPress", "onKeyDown", "onKeyUp", "onClick"], // events: Array // events which should be connected to the underlying editing // area, events in this array will be addListener with // capture=true captureEvents: [], _editorCommandsLocalized: false, _localizeEditorCommands: function(){ if(this._editorCommandsLocalized){ return; } this._editorCommandsLocalized = true; //in IE, names for blockformat is locale dependent, so we cache the values here //if the normal way fails, we try the hard way to get the list //do not use _cacheLocalBlockFormatNames here, as it will //trigger security warning in IE7 //in the array below, ul can not come directly after ol, //otherwise the queryCommandValue returns Normal for it var formats = ['p', 'pre', 'address', 'h1', 'h2', 'h3', 'h4', 'h5', 'h6', 'ol', 'div', 'ul']; var localhtml = "", format, i=0; while(format=formats[i++]){ if(format.charAt(1) != 'l'){ localhtml += "<"+format+">content"+format+">"; }else{ localhtml += "<"+format+">