Click here to Skip to main content
15,892,298 members
Articles / Desktop Programming / Windows Forms

tinyMCE HTML Editor in .NET WindowsForms

Rate me:
Please Sign up or sign in to vote.
3.75/5 (15 votes)
7 Jul 2008CPOL5 min read 141.4K   14.9K   71   18
tinyMCE WYSIWYG HTML editor in .NET WindowsForms
Image 1

Introduction

Did you in the past need to incorporate some HTML validating editor into your .NET desktop client? I did, so I started to look around for some components and found one, which is free and widely used, tinyMCE form Moxito.

One complication is that this one uses a browser to render edited content and is completely written in JScript, so one have to “hack” some browser control.

I’ll describe how to incorporate an Internet Explorer ActiveX into .NET form, join needed soap of tinyMCE into work file and load this work file into Internet Explorer ActiveX.

Background

As I said, tinyMCE is JScript wrapper over browser textarea control.

One possible solution is to use some browser control, load it with content and let the browser do the work with JScript. Let’s assume, we’re on Windows platform, so Internet Explorer is incorporated in the system.

So what we need is to store somewhere tinyMCE package, generate work HTML file, which contains edited text and links to tinyMCE scripts.

I decided to use users application folder, special subfolder will be created and tinyMCE package like a workfile will be stored.

Last thing to solve is to look over tinyMCE and check what it needs to work. And it’s not too much, in minimal version only few lines of code.
Let’s take a simple example based on tinyMCE package examples:

HTML
<html>
<head>
<title>tinyMCE
minimal example</title>
<!—SETTINGS
section -->
<!--
TinyMCE -->
<script type="text/javascript" src="../jscripts/tiny_mce/tiny_mce.js"></script>
<script type="text/javascript">
       tinyMCE.init({
              mode : "textareas,save",
              theme : "simple"
       });
</script>
<!-- /TinyMCE -->
</head>
<body>
<!—tiny MCE section -->
<form method="post" action="http://tinymce.moxiecode.com/dump.php?example=true">
       <textarea id="elm1" name="elm1" rows="15" cols="80" style="width: 80%">
        This is Edited Text
       </textarea>
</form>
</body>
</html>

Looking around this snippet, one can see we need to construct settings section and tiny MCE section. Settings are needed for tinyMCE to tell what plugins to load, what encoding and format of the text we need, etc., and the second section is textarea element encapsulated in form element, and this is what tinyMCE hooks and use as editing area.

Last point about “design” - it has to be reusable around few applications, so I encapsulated everything in one form class FrmHTMLBrowser, which is enabled to view or edit text. Why not in control? Well, tinyMCE is not pure control, we have to use some “hacks” with temp files, so it is a bit safer and more robust to use modal dialog box. Programmers, who will use this form, will be forced to use it more carefully and declaratively, not allowed to just paste control in designer wherever they think is fine.

One little thing to think about - browser needs to be JScript in path or subpath where workfile resides. That's why we have to place everything in one place. Basically, no matter where, if in ApplicationData\LocalSettings or \Temp or wherever else, but in one place.

Think also about running your application on terminal services - that's why I chose user ApplicationData. No problem with interfering forms.

Note: Problem with interfering forms will arise when the same applications will run concurrently in the same user profile and will be of the same editor type (same Type parameter in EditText). But this is not my case, if yours, try to use more specific storage or workfile indexing (find first "free" name). tinyMCE package can be shared, that's not a problem.

Using the Code

I used some helper methods to get everything to work in FrmHTMLBrowser.

C#
private string
getWorkPath(string subPath)

This one gets a path to temporary storage where work file and tinyMCE package are stored. It actually returns subfolder M_WORKPATH in Environment.SpecialFolder.LocalApplicationData.

C#
public void PrepareTinyMCE()

checks if tinyMCE already exists, if not, unzips package using ICSharp.ZipLib.

C#
public Stream GetResourceFile(string File)

gets stream from embedded resources.

C#
public string EditText(string Text, string Type, string CSSFile)

Public method for editing text, covers and calls showText. Type allows you to store work file with different name, so you can simultaneously call few
edit forms in one running user profile (theoretically, it’s not this case while form is shown modal) .

C#
private void showText(bool edit) 

Main Method

Here, HTML work file with links to tinyMCE Jscript is constructed and stored into a temporary file.
There’s a little bit custom code in this method, CSS replacement. The method looks in settings for [CSS] string and replaces it with passed path to CSS. Why is this useful? Well, when you’ll use this form, e.g., as editor for product descriptions over multiple regional databases of multiple companies, You’ll need to pass different CSSs got from database, for example.

After constructing work page and preparing tinyMCE package browser is navigated to work file by calling:

C#
axBrowser.Navigate(sDoc);

User stores text by pressing Save button in tinyMCE, that’s why in setting section, it’s declared tinyMCE has to use save plugin. One more hack, when save is used, one needs to cancel postback action of the form, otherwise will get tinyMCE error message. Looking into implementation leads to simple solution in showText :

C#
sb.AppendLine("<form method=\"\" action=\"\" onsubmit=\"return false;\">");

That’s it, smart guys in Moxito think about it, cancelling onsubmit will cancel error message too.

Last thing, how to get edited text back?

C#
m_text = ((mshtml.IHTMLDocument3)axBrowser.Document).getElementById("elm1").innerText;

Retyping root DOM document of the Internet Explorer control to IHTMLDocument3 allows you to access document elements represented by DOM model, so it’s easy to get content of textarea elm1, where tinyMCE resides.

Use FrmHTMLBrowser class to create editor enabled window just as in the example.

tinyMCE and settings are stored in resources as embedded resource, you can of course modify this solution and use disk storage or whatever you imagine.

Call FrmHTMLBrowser as you need, you'll get content of the editor back.

C#
FrmHTMLBrowser brw = new FrmHTMLBrowser();
ctlRtf.Text = brw.EditText(ctlRtf.Text, "tempfilename", "yourCSS.css");

Here in "tempfilename", you can specify name of work file, yourCSS.css will specify path to CSS file (of course again, it'll be copied into the work folder and make a relative path to package) , which will be used by tinyMCE to fillup Style combobox.

Links

Points of Interest

It's not my point of interest, HTML editors. Rather HW, Neural Networks, signal processing. But as in real life, I needed some HTML editor, and this one is very good and free under GPL.

History

  • Implemented, tested 2008/07/07

License

This article, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)


Written By
Architect ABB
Czech Republic Czech Republic
This member has not yet provided a Biography. Assume it's interesting and varied, and probably something to do with programming.

Comments and Discussions

 
QuestionCould you update the application for the current time? Pin
cod6610-Apr-20 2:29
cod6610-Apr-20 2:29 
QuestionWhere to get the "RepositoryTypeLib" library? Pin
cod6610-Apr-20 2:29
cod6610-Apr-20 2:29 
QuestionHow to fix the error "Could not load file or assembly Interop.SHDocVw"? Pin
cod6610-Apr-20 2:28
cod6610-Apr-20 2:28 
GeneralMy vote of 5 Pin
shehneh55934-Oct-13 9:42
shehneh55934-Oct-13 9:42 
GeneralSave button question Pin
cambiar11-Jan-09 9:43
cambiar11-Jan-09 9:43 
GeneralRe: Save button question Pin
Ondra Spilka31-May-09 22:42
professionalOndra Spilka31-May-09 22:42 
GeneralExactly like my solution Pin
Peter Gfader24-Jul-08 4:39
Peter Gfader24-Jul-08 4:39 
GeneralRe: Exactly like my solution Pin
Ondra Spilka31-May-09 22:41
professionalOndra Spilka31-May-09 22:41 
GeneralLoad errors; Pin
Glen Harvy12-Jul-08 3:26
Glen Harvy12-Jul-08 3:26 
GeneralRe: Load errors; Pin
Ondra Spilka12-Jul-08 4:45
professionalOndra Spilka12-Jul-08 4:45 
GeneralRe: Load errors; [modified] Pin
Glen Harvy12-Jul-08 12:46
Glen Harvy12-Jul-08 12:46 
GeneralRe: Load errors; Pin
Ondra Spilka31-May-09 22:43
professionalOndra Spilka31-May-09 22:43 
GeneralProblem Pin
Wadood Marashi11-Jul-08 20:37
Wadood Marashi11-Jul-08 20:37 
GeneralRe: Problem Pin
Ondra Spilka12-Jul-08 4:48
professionalOndra Spilka12-Jul-08 4:48 
GeneralRe: Problem Pin
Wadood Marashi13-Jul-08 22:15
Wadood Marashi13-Jul-08 22:15 
GeneralRe: Problem Pin
Krishan Kumar Gaurav116-Jul-10 2:18
Krishan Kumar Gaurav116-Jul-10 2:18 
QuestionRe: Problem Pin
CroweMan4-Sep-10 11:03
CroweMan4-Sep-10 11:03 
General[Message Removed] Pin
Mojtaba Vali8-Jul-08 18:12
Mojtaba Vali8-Jul-08 18:12 
Spam message removed

General General    News News    Suggestion Suggestion    Question Question    Bug Bug    Answer Answer    Joke Joke    Praise Praise    Rant Rant    Admin Admin   

Use Ctrl+Left/Right to switch messages, Ctrl+Up/Down to switch threads, Ctrl+Shift+Left/Right to switch pages.