Skip to content

Sitecore forum module – using TinyMCE instead of FreeTextBox

February 20, 2009

I wanted to replace the default WYSIWYG editor supplied with the Sitecore forum module (FreeTextBox) with TinyMCE, as it has better cross-browser compatibility.

Here’s how I did it…

I downloaded TinyMCE and extracted the files into a subfolder of my Sitecore filesystem at /js/tiny_mce. I also created a separate Javascript include file – /js/tiny_mce_init.js – to initialise the TinyMCE editor:

tinyMCE.init({
	// General options
	mode : "textareas",
	theme : "advanced",
	plugins : "safari,advimage,advlink,emotions,iespell,inlinepopups,insertdatetime,preview,media,searchreplace,print,contextmenu,paste,fullscreen,xhtmlxtras",

	// Theme options
	theme_advanced_buttons1 : "undo,redo,|,cut,copy,paste,pastetext,pasteword,|,search,replace,|,bold,italic,underline,strikethrough,sub,sup,|,forecolor,backcolor,|,bullist,numlist,|,outdent,indent,blockquote",
	theme_advanced_buttons2 : "link,unlink,anchor,|,image,media,|,cite,abbr,acronym,attribs,|,insertdate,inserttime,charmap,emotions,iespell,|,removeformat,cleanup,code,|,fullscreen,preview,print,|,help",
	theme_advanced_buttons3: "",
	theme_advanced_toolbar_location : "top",
	theme_advanced_toolbar_align : "left",
	theme_advanced_statusbar_location : "bottom",
	theme_advanced_resizing : true,
	theme_advanced_resize_horizontal : false,

	// Example content CSS (should be your site CSS)
	content_css : "/styles/style-editor.css"
});

I also wanted to use the ASP.NET compressor for TinyMCE, which “…gzips all javascript files in TinyMCE to a single streamable file. This makes the overall download size 75% smaller and reduces the number of requests to the web server. The initialization time for TinyMCE will also be reduced dramatically by using this script.”

I downloaded the compressor and placed the tiny_mce_gzip.js and tiny_mce_gzip.aspx files in my /js/tiny_mce folder. I also copied the ICSharpCode.SharpZipLib.dll into the bin folder of my Sitecore web application. (NB if you need the latest version of this dll, you can get it here.)

To initialise the compressor, I had to create another Javascript file – /js/tiny_mce/tiny_mce_gzip_init.js – which looks like this:

tinyMCE_GZ.init({
   plugins : "advimage,safari,advlink,emotions,iespell,inlinepopups,insertdatetime,preview,media,searchreplace,print,contextmenu,paste,fullscreen,xhtmlxtras",
   themes : 'advanced',
   languages : 'en',
   disk_cache : true,
   debug : false
});

Not completely sure if this is necessary, but to be on the safe side, I added the path to the compressor .aspx file to IgnoreUrlPrefixes in the Sitecore Web.config file.

I then created a class in a separate web application project (with post-build event set to xcopy the dll into the Sitecore application’s bin folder) which inherits from a TextBox and implements the ITextEditor interface. In this class, we override the OnLoad method to inject the appropriate script include blocks.

using System;
using System.Data;
using System.Configuration;
using System.Web;
using System.Web.Security;
using System.Web.UI;
using System.Web.UI.WebControls;
using System.Web.UI.WebControls.WebParts;
using System.Web.UI.HtmlControls;
using CommunityServer.Controls;

namespace MT.Flag.LivingLife.Controls
{

public class MTTinyMCE : System.Web.UI.WebControls.TextBox, ITextEditor
{
public MTTinyMCE()
: base()
{

}

//we can probably remove this
public void Configure()
{
if (this.Height.IsEmpty)
this.Height = Unit.Pixel(400);

if (this.Width.IsEmpty)
this.Width = Unit.Percentage(100);

if (this.Rows == 0)
this.Rows = 20;

if (this.Columns == 0)
this.Columns = 20;

}

protected override void OnLoad(EventArgs e)
{
this.TextMode = TextBoxMode.MultiLine;
base.OnLoad(e);
Configure();

// register TinyMCE client script
if (!this.Page.ClientScript.IsClientScriptIncludeRegistered(“tinymce”))
{
this.Page.ClientScript.RegisterClientScriptInclude(“tinymce”, this.Page.Request.ApplicationPath.TrimEnd(‘/’) + “/js/tiny_mce/tiny_mce_gzip.js”);
this.Page.ClientScript.RegisterClientScriptInclude(“tinymcegzipinit”, this.Page.Request.ApplicationPath.TrimEnd(‘/’) + “/js/tiny_mce/tiny_mce_gzip_init.js”);
this.Page.ClientScript.RegisterClientScriptInclude(“tinymceinit”, this.Page.Request.ApplicationPath.TrimEnd(‘/’) + “/js/tiny_mce_init.js”);
}
}

public bool IsRichTextCapable
{
get { return true; }
}

bool _isAdmin = false;

public string StyleName
{
get { throw new NotImplementedException(); }
set { throw new NotImplementedException(); }
}

public bool EnableHtmlModeEditing
{
get { return _isAdmin; }
set { _isAdmin = value; }
}

}
}

The default text editor for the Forum module is defined in the /communityserver.config file. I changed the textEditorType attribute of the <Core> node to match the class and assembly of the new class above:

  

All done, and pretty painless in the end. Thanks to Andrey Kovalenko for pointing me in the right direction.

Leave a Comment

Leave a comment